단어의 이진 스플릿 합계 계산


22

s인쇄 가능한 ASCII 문자를 입력으로 포함 하는 문자열을 가져 와서 "이진 분할 합계"를 출력하십시오. 설명이 필요하십니까?

이진 분할 합계는 어떻게 얻습니까?

A4다음 설명에서 문자열 을 예로 사용하겠습니다 .

  • 각 문자를 7 비트 ASCII 문자로 취급하여 문자를 이진으로 변환

    A -> ASCII 65 -> 1000001
    4 -> ASCII 52 -> 0110100
    
  • 이진수를 새로운 이진수로 연결

    A4 -> 1000001 & 0110100 -> 10000010110100
    
  • 결코 청크에 새 진수 분할 1을 가질 수 0는 왼쪽에 있습니다. 연속적인 1s를 분할해서는 안됩니다 .

    10000010110100 -> 100000, 10, 110, 100
    
  • 이 이진수를 십진수로 변환

    100000, 10, 110, 100 -> 32, 2, 6, 4
    
  • 이 숫자의 합을 취하십시오.

    32 + 2 + 6 + 4 = 44
    

따라서 문자열의 출력은 A4이어야합니다 44.


테스트 사례 :

a
49

A4
44

codegolf
570

Hello, World!
795

2
ASCII 변환 단계가 없으면 단계 2 다음에 (십진수) 숫자를 입력으로 사용하는 것이 더 좋은 도전 일 것입니다.
xnor

글쎄요 8372.
xnor

1
@ xnor, 당신이 옳을 수도 있고 더 깨끗할 것입니다. 나는 옥타브에서 이것을 해결하는 것이 재미 있었고, 다른 사람들도 그것을 해결하는 것을 즐기기를 바랍니다 :)
Stewie Griffin

답변:


12

파이썬 2 , 86 81 76 바이트

-5 바이트 덕분에 Adnan
-5 바이트 덕분에 xnor

s=0
for c in input():s=s*128+ord(c)
print eval(bin(s).replace('01','0+0b1'))

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

for c in input():s=s*128+ord(c)숫자로 ASCII 변환을 수행하는 경우, 7 번 *128왼쪽으로 이동 s(1 및 2 단계)
eval(('0'+new_bin).replace('01','0+0b1'))하여 분할 및 합계 (3, 4 및 5 단계)하는 데 사용됩니다.


와 좋은 트릭 eval! ASCII 변환을 수행하면 일부 바이트가 절약됩니다.
xnor

7

젤리 , 13 바이트

Oḅ128BŒg;2/ḄS

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

작동 원리

Oḅ128BŒg;2/ḄS  Main link. Argument: s (string)

O              Ordinal; map characters to their code points.
 ḅ128          Unbase 128; convert the resulting list from base 128 to integer.
     B         Binary; Convert the resulting integer to base 2.
      Œg       Group consecutive, equal bits.
        ;2/    Concatenate all non-overlapping pairs.
           Ḅ   Unbinary; convert from base 2 to integer.
            S  Take the sum.

전에는 기본 변환의 요령을 놓쳤습니다.
Jonathan Allan

아, 참 좋은 트릭!
Adnan

6

MATL , 14 바이트

YB!'1+0*'XXZBs

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

설명

'A4'예를 들어 입력 을 고려하십시오 .

YB        % Implicit input. Convert to binary using characters '0' and '1'. 
          % Gives a char matrix, where each row corresponds to a number
          % STACK: ['1000001'; '0110100']
!         % Transpose. This is necessary because MATL uses column-major 
          % order when linearizing a matrix into a vector
          % STACK: ['10'; '01'; '01'; '00'; '01'; '00'; '10']
'1+0*'    % Push this string: regexp pattern
          % STACK: ['10'; '01'; '01'; '00'; '01'; '00'; '10'], '1+0*'
XX        % Regexp. Linearizes the first input into a row (in column-major
          % order), and pushes a cell array of substrings that match the
          % pattern given by the second input
          % STACK: {'100000'; '10'; 110'; '100'}
ZB        % Convert each string into a decimal number. Gives numeric vector
          % STACK: [32; 2; 6; 4]
s         % Sum. Implicitly display
          % STACK: 44

5

05AB1E , 18 바이트

암호:

Çžy+b€¦JTR021:2¡CO

설명:

Ç                   # Take the ASCII value of each character
 žy+                # Add 128 to each value (to pad each with enough zeros)
    b               # Convert to binary
     €¦             # Remove the first character
       J            # Join the array
        TR021:      # Replace 01 by 021
              2¡    # Split on the number 2
                C   # Convert from binary to decimal
                 O  # Sum them all up

05AB1E 인코딩을 사용합니다 . 온라인으로 사용해보십시오!



3

자바 스크립트 (ES6), 97 92 바이트

s=>eval(s.replace(/./g,c=>(128+c.charCodeAt()).toString(2).slice(1)).replace(/1+/g,'+0b$&'))

편집 : @ ConorO'Brien의 도움으로 5 바이트를 저장했습니다.


내 자신의 솔루션도 97 바이트였습니다. s=>eval([...s].map(e=>(e.charCodeAt()+128).toString(2).slice(1)).join``.replace(/1+0*/g,'+0b$&'))Replace 메소드를 사용하여 바이트를 저장할 수 있다고 생각합니다
Conor O'Brien

1
@ ConorO'Brien 바이트 이상이라고 생각합니다!
Neil

Oo, n
c.e

3

apt , 18 12 바이트

c_¤ùT7Ãò< xÍ
c_           // Firstly, take the input and map over it as charcodes.
  ¤          // Take the binary representation of each item
   ùT7       // and left-pad it with zeroes to standardize the items.
      Ã      // After all of the above,
       ò<    // partition the result where ever a 0 precedes a 1.
          xÍ // Then sum the numbers from base 2.

입력을 단일 문자열로 사용합니다.
다른 답변에서 사용 된 128 또는 256 추가를 시도했지만 0 패딩은 사용하기가 더 짧았습니다.

ETHproductionsOliver 덕분에 전체 6 바이트를 줄였습니다 .

여기서 사용해보십시오.


: 당신은 여기에 더 자동 기능을 사용할 수 있습니다 òÈ<YÃ할 수있다 ò<(공간을 후행), 그리고 Ën2Ãx할 수 있습니다 xn2. T대신 0쉼표로 저장할 수도 있습니다 . (또한 궁금한 점이 있거나 골프와 관련하여 도움이 필요하시면 Japt 대화방 에 참여하십시오. )
ETHproductions

@ETHproductions 다시 한번 감사드립니다. 특히 T트릭에 대해 변수를 사용할 수 있다는 것을 몰랐습니다. 매우 편리합니다. 자동 함수 xn2는 컴파일 할 때 약간 이상하게 보이 x("n", 2)므로이면의 논리를 완전히 이해하기 전에 약간의 시간이 걸릴 것이라고 생각합니다. 귀하의 도움으로 Japt 솔루션은 이제 Jelly 답변 과 함께 첫 번째 장소에 연결됩니다 .
Nit

ETHproductions는 최근에 바로 가기를 만들어 n2: Í. 아직 TIO에 도달하지는 않았지만 여기에서 사용할 수 있습니다. ethproductions.github.io/japt/?v=1.4.5&code=Y1+k+VQ3w/…
Oliver

@Oliver 와우, 그것은 매우 빠른 가장자리이며, 아직 인터프리터 바로 가기 참조에서도 다루지 않습니다. 고마워요!
Nit

2

젤리 , 16 15 바이트

-1 데니스에 바이트 감사 (전체 평평하게 잘 때 1 평평 할 필요가 없습니다 - 교체 ;/와 함께 F)

O+⁹Bṫ€3FŒg;2/ḄS

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

방법?

O+⁹Bṫ€3FŒg;2/ḄS - Main link: list of characters, s    e.g. "A4"
O               - cast to ordinal (vectorises)        [65,52]
  ⁹             - literal 256
 +              - add (vectorises)                    [321, 308]
   B            - convert to binary (vectorises)      [[1,0,1,0,0,0,0,0,1],[1,0,0,1,1,0,1,0,0]]
    ṫ€3         - tail €ach from index 3              [[1,0,0,0,0,0,1],[0,1,1,0,1,0,0]]
       F        - reduce with concatenation           [1,0,0,0,0,0,1,0,1,1,0,1,0,0]
        Œg      - group runs of equal elements        [[1],[0,0,0,0,0],[1],[0],[1,1],[0],[1],[0,0]]
          ;2/   - pairwise reduce with concatenation  [[1,0,0,0,0,0],[1,0],[1,1,0],[1,0,0]]
             Ḅ  - convert from binary (vectorises)    [32,2,6,4]
              S - sum                                 44

1
;/로 교체 할 수 있습니다 F.
데니스

2

PHP, 116 바이트

for(;$c=ord($argn[$i++]);)$r.=sprintf("%07b",$c);$t=mb_split("(?<=0)(?=1)",$r);echo array_sum(array_map(bindec,$t));

온라인 버전

PHP, 117 바이트

for(;$c=ord($argn[$i++]);)$r.=sprintf("%07b",$c);$t=preg_split("#0\K(?=1)#",$r);echo array_sum(array_map(bindec,$t));

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

PHP, 120 바이트

for(;$c=ord($argn[$i++]);)$r.=sprintf("%07b",$c);preg_match_all("#1+0+#",$r,$t);foreach($t[0]as$b)$s+=bindec($b);echo$s;

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

또는

for(;$c=ord($argn[$i++]);)$r.=sprintf("%07b",$c);preg_match_all("#1+0+#",$r,$t);echo array_sum(array_map(bindec,$t[0]));


1

[F #], 249245 바이트

open System
let rec c a=function|[]->[a]|'0'::'1'::y->(a+"0")::(c""('1'::y))|x::y->c(a+string x)y
let x i=c""(String.Join("",(Seq.map(fun c->Convert.ToString(int c,2).PadLeft(7,'0'))i))|>Seq.toList)|>Seq.map(fun c->Convert.ToInt32(c,2))|>Seq.sum

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

참고 : tio.run의 버전은 헤더에 "open System"이 있으며 위 코드에 카운트를 추가했습니다. 수입 규칙에 대해 잘 모르겠습니다.

언 골프

let rec convert acc = function
    | [] -> [acc]
    | '0'::'1'::xs -> (acc + "0") :: (convert "" ('1'::xs))
    | x::xs -> convert (acc + string x) xs

let calculateSum input =
    let binary = Seq.map (fun x -> Convert.ToString(int x, 2).PadLeft(7, '0')) input

    String.Join("", binary)
    |> Seq.toList
    |> convert ""
    |>Seq.map (fun x -> Convert.ToInt32(x, 2))
    |>Seq.sum

경우 open SystemC #의 것과 동일 using System;다음 예는 계산에 포함해야합니다. F #에서 할 수 있다면 System에 대한 모든 것을 정규화 할 수 있습니다. 예를 들어, C # System.Console...에서using System;Console...
TheLethalCoder

@TheLethalCoder 그렇습니다. 또한 이것을 분명히 해주셔서 감사합니다 :) "open .."버전은 String뿐만 아니라 해당 네임 스페이스에 라이브로 변환하기 때문에 선택했습니다.
Brunner


0

J , 34 바이트

[:+/@(,#.;.1~1,1=2#.\,)(7#2)#:3&u:

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

설명

[:+/@(,#.;.1~1,1=2#.\,)(7#2)#:3&u:  Input: array of characters S
                              3&u:  Get ASCII values of each character
                       (7#2)        Array with 7 copies of the value 2
                            #:      Convert each value to a base 2 array with length 7
[:  (                 )             Operate on those binary values
                     ,                Flatten it
                 2  \                 For each infix of size 2
                  #.                    Convert it to decimal from binary
               1=                     Test each value for equality to 1
             1,                       Prepend a 1
      ,                               The flattened binary values
         ;.1~                         Chop that at each occurrence of a 1
       #.                               Convert each chop from binary to decimal
 +/@                                Reduce by addition

0

수학 193 바이트

f=FromDigits;l=Flatten;(S=Split@l@Table[PadLeft[IntegerDigits[ToCharacterCode@#,2][[k]],7],{k,StringLength@#}];Plus@@Table[f[RealDigits@f@Join[S[[i]],S[[i+1]]],2],{i,1,Length@S-1,2}]+Last@l@S)&

당신은 수행하여 7 바이트를 저장할 수 있습니다 f=FromDigits;l=Flatten;시작시, 다음으로 두 기능의 모든 인스턴스를 교체 f하고 l.
numbermaniac

0

J , 40 바이트

+/>#.&.>(1,}.|.1 0 E.|.b)<;.1 b=.,#:a.i.

용법:

+/>#.&.>(1,}.|.1 0 E.|.b)<;.1 b=.,#:a.i.'A4'

44를 반환


0

클로저, 150 바이트

#(loop[[c & C](for[i % j[64 32 16 8 4 2 1]](mod(quot(int i)j)2))p 0 r 0 R 0](if c(if(=(dec c)p 0)(recur C c 1(+ R r))(recur C c(+(* 2 r)c)R))(+ R r)))

글쎄, ASCII에서 바이트로의 변환이 이것보다 짧기를 바랐다. 실제 루프 바디는 r현재 결과 R를 누적하고 총 결과를 누적하는 데 사용하여 매우 짧습니다 . 이전 비트 p0현재 비트 c이고 현재 비트 가 1새로운 청크를 분할하고에 누적 R되면 그렇지 않으면를 업데이트 r하고 그대로 유지 R합니다.


0

파이썬 123 바이트

lambda w:sum(map(lambda x:int(x,2),"".join(map(lambda x:bin(ord(x))[2:].zfill(7),list(w))).replace("01","0:1").split(":")))

Martin Ender 덕분에 업데이트되었습니다.


1
PPCG에 오신 것을 환영합니다! 모든 답변은 전체 프로그램 또는 호출 가능한 함수 여야합니다 (입력이 하드 코딩 된 변수에 저장된 스 니펫과 반대). 그러나 함수의 이름을 지정할 수 없으므로 a를 포함하면 lambda w:대답이 유효합니다.
Martin Ender

미안, 아마 그 말을 잘하지 못했습니다. a) 입력이 하드 코드되어 있기 때문에 편집이 여전히 유효하지 않습니다. b) 전체 프로그램 인 경우 실제로 결과를 인쇄하지 않습니다. 전체 프로그램을 사용하려면 표준 입력 또는 명령 행 인수에서 입력을 읽고 결과를 표준 출력으로 인쇄해야합니다. 그렇기 때문에을 추가하여 함수로 제출하면 가장 쉽다고 말했습니다 lambda w:.
Martin Ender

오, 알았어. 알았어. f = lambda w : sum (map (lambda x : int (x, 2), "). join (map (lambda x : bin (ord (x)) ) [2 :]. zfill (7), list (w))). replace ( "01", "0 : 1"). split ( ":")))
ShadowCat

그렇습니다, 그것은 유효합니다. f=이름없는 함수를 허용하기 때문에 (재귀 호출에 대한 함수 이름을 참조 하지 않는 한)조차 필요하지 않습니다 .
Martin Ender

0

K (oK) , 31 바이트

해결책:

+/2/'_[;x]&x&~~':x:,/(7#2)\'`i$

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

예 :

+/2/'_[;x]&x&~~':x:,/(7#2)\'`i$,"a"
49
+/2/'_[;x]&x&~~':x:,/(7#2)\'`i$"A4"
44
+/2/'_[;x]&x&~~':x:,/(7#2)\'`i$"codegolf"
570
+/2/'_[;x]&x&~~':x:,/(7#2)\'`i$"Hello, World!"
795

설명:

ASCII 값으로 변환하고, 7 비트 이진수로 변환하고, 평평하게하고, 다른 곳을 찾거나, 원래 목록과 비교하여 1s가 다른 곳을 찾습니다 . 이 지수를 자르고 다시 십진수로 변환하고 요약하십시오.

+/2/'_[;x]&x&~~':x:,/(7#2)\'`i$ / the solution
                            `i$ / convert to integer
                     (7#2)      / draw from 2, 7 times => 2 2 2 2 2 2 2
                          \'    / decode each (convert to binary)
                   ,/           / flatten
                 x:             / save as x
             ~~':               / not-not-each previous (differ)
            &                   / and with
           x                    / x
          &                     / indices where true
     _[;x]                      / projection, cut x at ...
  2/'                           / encode each (convert from binary)
+/                              / sum up

보너스

K4 에서 31 바이트 버전도 관리 했지만 TIO가 없으므로 oK 솔루션을 게시하고 있습니다.

+/2/:'_[;x]@&x&~~':x:,/1_'0b\:'

0

APL (Dyalog) , 30 바이트

{+/2⊥¨(1∘+⊆⊢)∊¯7↑¨2⊥⍣¯1¨⎕UCS⍵}

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

방법?

⎕UCS⍵ -유니 코디 파이

2⊥⍣¯1¨ -바이너리로 각각 인코딩

¯7↑¨ -0에서 7 자리까지 왼쪽으로 채 웁니다.

-평평하게하다

1∘+⊆⊢ -자체 파티션은 1 씩 증가

2⊥¨ -바이너리에서 각각 디코딩

+/ -합계

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.