비트 런 다운


43

integer가 주어지면 n > 0가장 긴 연속 시퀀스의 길이 0또는 1이진 표현으로 출력됩니다.

  • 6110이진수 로 작성 됩니다. 가장 긴 시퀀스는입니다 11.2
  • 16100004
  • 89311011111015
  • 13373711010001101000000110116
  • 111
  • 99655461001100000001111111010107


32 비트 또는 64 비트와 같은 정수 크기의 경계를 가정 할 수 있습니까?
xnor

@xnor yes int가 최대 32 비트라고 가정 할 수 있습니다
Arnaud

답변:


30

파이썬 2 , 46 45 바이트

f=lambda n,k=1:`k`in bin(n^n/2)and-~f(n,k*10)

온라인으로 사용해보십시오!

작동 원리

XOR 연산함으로써 , NN / 2 (분할하여 2 본질적 마지막 비트 Off 자르면), 우리는 새로운 정수 얻을 m 그 해제 비트 인접한 비트 일치 나타내는 N을 .

예를 들어, n = 1337371 인 경우 다음이 있습니다.

n    = 1337371 = 101000110100000011011₂
n/2  =  668685 =  10100011010000001101₂
m    = 1989654 = 111100101110000010110₂

이것은 가장 긴 0을 찾는 작업을 줄입니다. 양의 정수의 이진 표현은 항상 1로 시작하므로 m 의 이진 표현에 나타나는 가장 긴 10 * 자릿수 를 찾으려고 노력할 것 입니다. 이것은 재귀 적으로 수행 될 수 있습니다.

k1 로 초기화하십시오 . f 가 실행될 때마다 먼저 k 의 10 진수 표현이 m 의 2 진 표현으로 나타나는지 테스트합니다 . 그렇다면 k10 을 곱하고 f를 다시 호출 합니다. 그렇지 않으면 오른쪽의 코드가 and실행되지 않고 False 를 반환 합니다.

이를 위해 먼저 계산 bin(k)[3:]합니다. 이 예에서, bin(k)반환 '0b111100101110000010110', 그리고 0b1처음에이 제거됩니다 [3:].

이제 -~재귀 호출 전의 f 는 재귀 적으로 호출 될 때마다 False / 0을 한 번 증가시킵니다 . 일단 (10)}가 {J ( 1 이어서 J에서 의 반복 0 의 이진 표현으로 표시되지 않음) K 에서 제로의 최장 k는 길이 갖는다 J을 - 1 . 이후 J - 1 의 연속 제로 K가 표시 J에서 의 정합 인접한 비트 N을 , 원하는 결과는 J 우리가 증가하여 수득 무엇 인 거짓 / 0j


2
이것은 정말 영리합니다!
CraigR8806

1
와우, 그것은 영리하다. 생각조차 못 했어
HyperNeutrino

10의 거듭 제곱으로 멋진 트릭이지만 L로 길게되지 않습니까?
xnor

@xnor 결국에는 데이터 유형 제한 일뿐입니다. C, JavaScript 및 PHP 답변도이 문제로 어려움을 겪고 있습니다.
데니스

프로덕션 환경에서 사용하면 심각하게 유지 관리 할 수 ​​없습니다. 한마디로 (ghehe) 골프 달성, 하나의 구멍 :)
JAK

17

파이썬 2, 46 바이트

f=lambda n,r=1:max(r,n and f(n/2,1+~-n/2%2*r))

온라인으로 사용해보십시오

추출물 이진수를 n반복적으로 취함으로써 역으로 n/2n%2. r마지막 두 자리가 같지 않은 경우 0으로 재설정 한 다음 1을 추가 하여 현재 같은 자리 수 의 길이를 추적합니다 .

이 표현 ~-n/2%2은 마지막 두 자리가 같은지, 즉 n0 또는 3 모듈로 4 인지를 나타내는 지표입니다 . 마지막 두 자리를 함께 확인하면 이전 자리를 기억하는 것보다 짧게 나타납니다.



9

수학, 38 바이트

Max[Length/@Split[#~IntegerDigits~2]]&

또는

Max[Tr/@(1^Split[#~IntegerDigits~2])]&

9

파이썬, 53 바이트

import re;lambda g:max(map(len,re.findall('1+|0+',bin(g))))

익명의 람다 함수.



9

루비, 41 40 바이트

->b{("%b%b"%[b,~b]).scan(/1+/).max.size}

b 또는 그 역에서 가장 긴 '1'시퀀스를 찾으십시오.

1 바이트를 저장하는 manatwork 덕분에.


2
다른 버전은 확실하지 않지만 2.3.1에서는 사이에 공백이 필요하지 않습니다 %b.
manatwork

맞습니다, 음의 이진수는 ".."로 시작합니다. 감사.
GB

7

자바 스크립트 (ES6), 54 바이트

f=(n,r=0,l=1,d=2)=>n?f(n>>1,d^n&1?1:++r,r>l?r:l,n&1):l

비트 조작이 많은 재귀 솔루션. n입력을 r저장하고 현재 런 l의 길이를 저장하며 가장 긴 런의 길이를 d저장하며 이전 자릿수를 저장합니다.

테스트 스 니펫

f=(n,r=0,l=1,d=2)=>n?f(n>>1,d^n&1?1:++r,r>l?r:l,n&1):l

for(var i of [0,1,2,3,4,5,6,7,8,9,16,893,1337371]) console.log(`f(${i}): ${f(i)}`)


1
같은 생각이지만 더 많은 비트 연산을 사용하고 undefined를 0으로 변환하는 기본 변환을 활용합니다. 빌리십시오.f=(x,b,n,m)=>x?f(x>>1,x&1,n=x&1^b||-~n,m>n?m:n):m
edc65

7

루비, 51 44 43 바이트

기능 솔루션.

@manatwork는 마술로 만들어졌습니다.

->s{('%b'%s).scan(/0+|1+/).map(&:size).max}

연속적인 동일한 숫자 또는 연속적인 0s를 검사합니까?
ngenisis

2
893에 대한 잘못된 결과입니다.
orlp

@orlp는 더 이상 없습니다! : D
Value Ink

1
나는 첫 번째와 두 번째 솔루션을 결합 할 것입니다 : ->s{s.to_s(2).scan(/0+|1+/).map(&:size).max}.
manatwork

6

파이썬 2, 57 바이트

a=lambda n:n and max((n&-n|~n&-~n).bit_length()-1,a(n/2))

재귀 솔루션. 비트 마법에 대한 짧은 형식이있을 수 있습니다.


6

펄, 43 바이트

#!perl -p
\@a[$a+=$_-1+($_>>=1)&1||-$a]while$_;$_=@a

shebang을 하나로 계산하여 입력을 stdin에서 가져옵니다.

온라인으로 사용해보십시오!


Shebang은 0 바이트로 계산됩니다.
CalculatorFeline

메타에 대한 @CalculatorFeline 합의#!perl0이 아니라 0으로 계산됩니다 #!perl -p.
primo

@CalculatorFeline : -pPerl 명령 행에 어쨌든 인수 (예 : -e또는 -M5.010) 가 있다고 가정하면 비용 1 이므로 p하이픈 중 하나 바로 뒤에 들어갈 수 있습니다 . 은 #!perl(필요하지만) 무료입니다.

알아 둘만 한. .
CalculatorFeline

5

, 16 바이트

같은 자릿수의 런을 얻는 더 짧은 방법이 있어야합니다 ...

MX#*(TBa`1+|0+`)

명령 행 인수로 입력을받습니다. 온라인으로 사용해보십시오!

설명

     TBa          1st cmdline arg, To Binary
    (   `1+|0+`)  Find all matches of this regex
  #*              Map length operator to that list
MX                Get the maximum and autoprint it

5

펄 6 , 36 바이트

{(.base(2)~~m:g/1+|0+/)».chars.max}

설명:

{                                 }   # a lambda
  .base(2)                            # convert the argument to base 2
          ~~m:g/     /                # regex match, with global matching turned on
                1+|0+                 # match one or more 1, or one or more 0
 (                    )».chars        # replace each match by its length
                              .max    # take the maximum number

온라인으로 사용해보십시오 .


4

하스켈, 79 자

maximum.map length.group.i

어디

import Data.List
i 0=[]
i n=mod n 2:i(div n 2)

또는 ungolfed 버전에서 :

import Data.List
pcg :: Int -> Int
pcg = maximum . map length . group . intToBin

intToBin :: Int -> [Int]
intToBin 0 = []
intToBin n = n `mod` 2 : intToBin (n `div` 2)

설명:

intToBinint를 이진 숫자 목록으로 변환합니다 (먼저 lsb). group그룹 인접 서열, 예컨대 그 [1, 1, 0, 0, 0, 1]된다 [[1, 1],[0, 0, 0],[1]].maximum . map length각 내부 목록에 대해 길이를 계산하고 가장 긴 길이를 반환합니다.

편집 : 바이트를 절약 한 @xnor 및 @Laikoni 덕분에


2
groupPrelude에 기본적으로 포함되어 있지 않은 import Data.List경우이를 사용해야합니다.
xnor

1
당신이 대신 가드를 사용할 수 있습니다 let: i n|(q,r)<-n`quotRem`2=r:i q. Haskell 골프 팁을 참조하십시오 . quotRem일 수 있습니다 divMod. i 0=[]기본 케이스로 사용할 수 있다고 생각합니다 .
xnor

1
사용 divmod직접 심지어 짧은 : i n=mod n 2:i(div n 2).
Laikoni

3

Pyth, 7 바이트

heSr8.B

이진 문자열에서 실행 길이 인코딩을 수행 한 다음 가장 긴 실행이 마지막에 오도록 정렬 한 다음 목록의 마지막 요소 (가장 긴 실행)의 첫 번째 요소 (길이)를 가져옵니다.

의사 코드에서 :

'  S     ' sorted(
'   r8   '   run_length_encode(
'     .BQ'     bin(input()) ))  \
'he      '   [-1][0]

3

J , 21 바이트

[:>./#:#;.1~1,2~:/\#:

온라인으로 사용해보십시오!

설명

[:>./#:#;.1~1,2~:/\#:  Input: integer n
                   #:  Binary digits of n
              2   \    For each continuous subarray of 2 digits
               ~:/       Reduce it using not-equals
            1,         Prepend a 1 to those results
     #:                Binary digits of n
        ;.1~           Cut the binary digits at each location with a 1
       #                 Get the length of each cut
[:>./                  Reduce those lengths using maximum and return

3

MATLAB 71 바이트

m=1;a=diff(int8(dec2bin(a)));while(any(a==0)),m=m+1;a=diff(a);end;m

이것은 정수 변수 'a'를 이진 int8 배열로 변환 한 다음 결과에 0이 없을 때까지 결과를 차별화 해야하는 횟수를 계산합니다.

나 여기 처음이야. PCG 규칙에서 이러한 종류의 입력과 하나의 라이너가 허용됩니까?


3
PPCG에 오신 것을 환영합니다! 기본적으로 기능 또는 전체 프로그램 (코드 조각 제외) 만 허용됩니다. 귀하의 경우에는 수단은 입력 할 필요가 aa=input('');. 또한 일부 골프 조언 : ~a대신 a==0. 정말로 필요 int8합니까?)
Luis Mendo

3

옥타브 , 31 바이트

@(n)max(runlength(+dec2bin(n)))

온라인으로 사용해보십시오!

설명

이것은 내 MATL 답변의 번역입니다. 저의 초기 계획은 다른 접근 방식이었습니다 @(n)max(diff(find(diff([0 +dec2bin(n) 0])))). 그러나 Octave에는 runlength기능이 있습니다 (방금 알았습니다). 기본적으로 실행 길이 배열 만 출력하므로 원하는 결과는 max해당 배열의 결과입니다 . 출력 dec2bin함유 문자 배열 (문자열)이며, '0'그리고 '1', 사용 숫자 배열로 변환 할 필요가 +있기 때문에 runlength예상하는 수치 입력한다.



3

배쉬 (+ coreutils, + GNU grep), 33, 32 바이트

EDITS :

  • 빼기 1 바이트 ( grep 표현식 주위의 따옴표 제거 )

골프

dc -e2o$1p|grep -Po 1+\|0+|wc -L

설명

 #Convert to binary
 >dc -e2o893p
 1101111101

 #Place each continuous run of 1es or 0es on its own line
 >dc -e2o893p|grep -Po '1+|0+'
 11
 0
 11111
 0
 1

 #Output the length of the longest line
 >dc -e2o893p|grep -Po '1+|0+'|wc -L
 5

온라인으로 사용해보십시오!


AFAIK, grep은 bash 또는 coreutils의 일부를 형성하지 않지만 자체적으로 유지 관리 및 배포됩니다 . dc에 대해서는 확실하지 않지만 GNU 세계에서는 독립형 도구였습니다. coreutils의 유일한 구성 부분은 wc입니다.
Moreaki

@Moreaki, grep 은 POSIX이므로 쉘 기반 답변은 이미 사용 가능하다는 것을 의미합니다. dc 는 POSIX는 아니지만 거의 모든 * Nix 시스템의 표준 부분이므로 일반적으로 별도의 종속성으로 언급되지 않습니다.
zeppelin

나는 우리가 여기에 두 가지 다른 생각의 기차에 있다고 생각합니다. 이것은 사실이 아닙니다. 처음 읽을 때이 정보가 혼란 스러웠습니다. macOS로 제공되는 bash 쉘에서 솔루션을 시도하면 작동하지 않습니다. coreutils를 설치했는지 여부는 중요하지 않습니다. 제대로 작동하려면 GNU grep이 필요합니다.
Moreaki

@Moreaki, 그렇습니다. 나는 + coreutils라고 말할 때 GNU 시스템을 암시하지만 항상 그런 것은 아닙니다. 제목을 더 정확하게 업데이트했습니다.
zeppelin은


2

C #, 106 바이트

n=>{int l=1,o=0,p=0;foreach(var c in System.Convert.ToString(n,2)){o=c!=p?1:o+1;l=o>l?o:l;p=c;}return l;};

형식화 된 버전 :

System.Func<int, int> f = n =>
{
    int l = 1, o = 0, p = 0;
    foreach (var c in System.Convert.ToString(n, 2))
    {
        o = c != p ? 1 : o + 1;

        l = o > l ? o : l;

        p = c;
    }

    return l;
};

공백이 제거 된 상태에서 118 바이트의 인덱스로 문자열에 액세스하는 대체 방법 :

System.Func<int, int> f2 = n =>
{
    var s = System.Convert.ToString(n, 2);

    int l = 1, c = 1, i = 0;

    for (; i < s.Length - 1; )
    {
        c = s[i] == s[++i] ? c + 1 : 1;
        l = l < c ? c : l;
    }

    return l;
};

2

자바 스크립트, 66 바이트

x=>Math.max(...x.toString(2).split(/(0+|1+)/g).map(y=>y.leng‌​th))

코드에 대한 manatwork 덕분에 .

설명

x.toString(2)

숫자를 이진 문자열로 변환합니다.

split(/(0+|1+)/g)

각기 다른 문자 (0 또는 1)를 분할합니다 (이 정규식은 빈 공간을 캡처하지만 무시할 수 있음)

map(y=>y.length)

배열의 각 요소마다 길이를 가져 와서 반환 된 배열에 넣습니다.

...

배열을 인수 목록으로 변환 ([1,2,3]-> 1,2,3)

Math.max()

인수에서 가장 큰 수를 얻으십시오.


1
영감을 얻기 위해 Value Ink루비 솔루션 을 인정함으로써 이를로 변환 할 수 있습니다 x=>x.toString(2).split(/(0+|1+)/g).map(y=>y.length).sort().pop(). 또는 같은 길이 : x=>Math.max(...x.toString(2).split(/(0+|1+)/g).map(y=>y.length)).
manatwork

3
정렬 함수에 조건자를 추가해야 할 수도 있습니다 sort((a,b)=>b-a). 기본적으로, 정렬 기능은 배치 10사이에 12.
Mama Fun Roll

또는 manatwork가 제안한 것처럼 Math.max를 사용할 수 있습니다.
Mama Fun Roll

Wtf이지만 숫자입니다. JS 부탁합니다.

2

Wonder , 27 바이트

max.map#len.mstr`0+|1+`g.bn

용법:

(max.map#len.mstr`0+|1+`g.bn)123

이진수로 변환하고 0과 1의 각 시퀀스를 일치시키고 각 일치의 길이를 가져오고 최대 값을 얻습니다.


입력을 바이너리로 변환합니까?
Laikoni

oooooh 나는 그 부분을 놓쳤다. 빠른 수정 : P
Mama Fun Roll

2

배치, 102 바이트

@set/a"n=%1/2,d=%1%%2,r=1+(%3+0)*!(0%2^d),l=%4-(%4-r>>5)
@if not %n%==0 %0 %n% %d% %r% %l%
@echo %l%

@ edc65의 답변 포트입니다. %2.. %4첫 번째 호출에서 비어있을 것이므로 표현식이 여전히 작동하는 방식으로 작성해야합니다. 가장 일반적인 경우는 다음 %3과 같이 작성해야 (%3+0)합니다. 또는 8 진수 %2만 같을 수 있기 때문에 더 쉽습니다 . 여기서 작동합니다. 빼기 만하면되므로 훨씬 쉬워졌습니다. Batch 에는 비교 연산자가 없으므로 비교 하는 데 사용됩니다 .010%2%4(%4-r>>5)lrset/a


2

Dyalog APL , 22 바이트

익명의 기능 기차

⌈/∘(≢¨⊢⊂⍨1,2≠/⊢)2⊥⍣¯1

⌈/∘(... 다음 익명 함수 트레인의 결과 최대 값 ...

≢¨  각각의 탈리

⊢⊂⍨ 인수의 분할. 분할은 다음의 분할에 의해 결정됩니다.

1, 앞에 붙인 사람

2≠/ 짝이 아닌

 논쟁 거리

) 에 적용

2⊥⍣¯1 -베이스 -2에서 음수로 한 번 적용 (즉,베이스 -2에서 한 번)

 논쟁 거리

TryAPL 온라인!


2

apt, 15 바이트

2o!q¢ c ml n gJ

온라인으로 테스트하십시오! 또는 모든 테스트 사례를 한 번에 확인하십시오 .

작동 원리

                 // Implicit: U = input integer, J = -1
2o               // Create the range [0...2), or [0,1].
  ! ¢            // Map each item Z in this range to U.s(2)
   q             //                                        .q(Z).
                 // This returns the runs of 1's and 0's in the binary
                 // representation of U, respectively.
      c          // Flatten into a single list.
        ml       // Map each item Z to Z.length.
           n gJ  // Sort the result and grab the item at index -1, or the last item.
                 // This returns the largest element in the list.
                 // Implicit: output result of last expression

2

R, 45 34 바이트

max(rle(miscFuncs::bin(scan()))$l)

@rturnbull 및 @plannapus 덕분에 바보 같은 오해가 수정되었습니다.


아마도 뭔가 빠졌지 만 입력이 정수가 아닌 이진수가 아닌가? 그리고 우리는 최대의 실행을 찾고 0또는 1뿐만 아니라, 0오른쪽?
rturnbull

@plannapus 나는 정직하게 모른다. 사양을 완전히 놓친 것 같습니다. 지금 수정했습니다.
Billywob

2

PowerShell , 78 74 73 바이트

([regex]::Matches([convert]::ToString("$args",2),'0+|1+')|% Le*|sort)[-1]

온라인으로 사용해보십시오!

그 .Net 메소드.

이것은 정규식을 사용하여 1과 0의 연속 시퀀스를 찾아 일치시킵니다. 그런 다음 결과 일치 객체 의 Length속성 (작은 알려진 매개 변수 집합을 사용하여 ForEach-Object1 바이트를 절약 하는 새로운 패턴으로 )을 가져옵니다. 그것들을 정렬하고 마지막 것 (가장 큰 것)을 출력합니다.


1

J, 27 바이트

>./>#&.>((1,2~:/\[)<;.1])#:

마일의 답변에 약간 다른 (그리고 불행히도 더 긴) 접근법 .

용법:

    >./>#&.>((1,2~:/\[)<;.1])#:893
5

설명

>./>#&.>((1,2~:/\[)<;.1])#:
                         #: Convert to base 2
        (               )   A fork
                       ]    Previous result
         (1,2~:/\[)         Find where each new sequence begins
                   <;.1     Cut the string of integers based on where each sequence begins and box them
    #&.>                    Count under open - open each box and count the items in it
>./>                        Open all the boxes and find the maximum value

나는 이것이 유효하지 않다고 생각합니다. 그것은 기능이 아니며 코드 조각이기도합니다.
코너 오브라이언

@ ConorO'Brien 좋아요, 나중에 다시 볼게요.
Gareth
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.