Bir kelimenin ikili bölünme toplamını hesaplayın


22

sGirdi olarak yazdırılabilir ASCII karakterleri içeren bir dize alın ve "ikili bölünme toplamını" çıktılayın. Bir açıklamaya mı ihtiyacınız var?

İkili bölünmüş toplamı nasıl elde edersiniz?

A4Aşağıdaki açıklamada dizeyi örnek olarak kullanacağız .

  • Her harfi 7 bit ASCII karakteri olarak ele alarak karakterleri ikiliye dönüştürün

    A -> ASCII 65 -> 1000001
    4 -> ASCII 52 -> 0110100
    
  • İkili sayıları yeni bir ikili sayı ile birleştir

    A4 -> 1000001 & 0110100 -> 10000010110100
    
  • Yeni ikili sayıyı, hiçbirinin soluna 1sahip olamayacağı parçalara bölün 0. Ardışık 1s'yi bölmemelisiniz.

    10000010110100 -> 100000, 10, 110, 100
    
  • Bu ikili sayıları ondalık sayıya dönüştür

    100000, 10, 110, 100 -> 32, 2, 6, 4
    
  • Bu sayıların toplamını al:

    32 + 2 + 6 + 4 = 44
    

Yani, dize için çıktı A4olmalıdır 44.


Test durumları:

a
49

A4
44

codegolf
570

Hello, World!
795

2
Bunun ASCII dönüşüm aşaması olmadan daha güzel bir meydan okuma olacağını düşünüyorum, sadece 2. adımdan sonra (ondalık) sayıyı girdi olarak alarak.
xnor

Eh, 8372aslında.
xnor

1
@ xnor, haklı olabilirsiniz ve daha temiz olurdu. Bunu Octave'da çözmeyi çok eğlendim ve umarım başkaları da çözmekten zevk alır :)
Stewie Griffin

Yanıtlar:


12

Python 2 , 86 81 76 bayt

-5 bayt teşekkürler Adnan
-5 bayt teşekkürler xnor

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

Çevrimiçi deneyin!

for c in input():s=s*128+ord(c)ASCII dönüşümünü sayısal olarak yapmak için, 7 kez *128sola kaymak için kullanılır s(1. ve 2. adımlar)
eval(('0'+new_bin).replace('01','0+0b1'))bölmek ve toplamak (3., 4. ve 5. adımlar).


Güzel numara eval! ASCII dönüşümünü yapmak, bazı baytları sayısal olarak kaydeder.
xnor

7

Jöle , 13 bayt

Oḅ128BŒg;2/ḄS

Çevrimiçi deneyin!

Nasıl çalışır

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.

Daha önce bu temel dönüşüm numarasını kaçırdım.
Jonathan Allan,

Ah, gerçekten güzel numara!
Adnan

6

MATL , 14 bayt

YB!'1+0*'XXZBs

Çevrimiçi deneyin!

açıklama

'A4'Bir örnek olarak girişi düşünün .

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 bayt

Kod:

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

Açıklama:

Ç                   # 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 kodlamasını kullanır . Çevrimiçi deneyin!



3

JavaScript (ES6), 97 92 bayt

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

Düzenleme: @ ConorO'Brien yardımı ile 5 bayt kaydedildi.


Benim çözümüm de 97 baytı: s=>eval([...s].map(e=>(e.charCodeAt()+128).toString(2).slice(1)).join``.replace(/1+0*/g,'+0b$&'))Bir bayttan tasarruf etmek için değiştirme yöntemimi kullanabilirsiniz, sanırım
Conor O'Brien,

1
@ ConorO'Brien Bir bayttan daha fazlası, sanırım!
Neil,

Demek ki: D
Conor O'Brien

3

Japt , 18 12 bayt

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.

Girişi tek bir dize olarak alır.
Diğer cevaplar tarafından kullanılan 128 veya 256 ilaveyi de denedim, fakat 0-dolgu kullanımı daha kısadı.

ETHproductions ve Oliver sayesinde, 6 baytlık bir dolu .

Burada dene.


Burada daha fazla otomatik işlev kullanabilirsiniz: òÈ<YÃolabilir ò<(sondaki boşlukla) ve Ën2Ãxolabilir xn2. Ayrıca virgülten tasarruf etmek için Tyerine kullanabilirsiniz 0. (Ayrıca, sorularınız olursa veya golf oynamaya yardımcı olmak istemeniz durumunda Japt sohbet odasında bize katılmaktan çekinmeyin :-))
ETHproductions

@ETHproductions Tekrar, özellikle Tnumara için, bunun için (ab) değişkenlerini kullanabileceğinizi bilmiyordum, bu çok kullanışlı. Otomatik işlev xn2derlendiğinde biraz garip görünüyor x("n", 2), bu yüzden arkasındaki mantığı tam olarak anlamadan biraz daha süreceğini düşünüyorum. Yardımınızla, Japt çözümü şimdi Jelly cevabı ile ilk etapta bağlı .
Nit

ETHproductions geçenlerde için bir kısayol yapılan n2: Í. Henüz TIO'yu vurmadı
Oliver

@Oliver Wow, çok kanama kenarı, henüz yorumlayıcı kısayolları referansında yer almadı. Çok teşekkürler!
Nit

2

Jöle , 16 15 bayt

-1 Dennis bayt sayesinde (tam düzleştirmek ince olduğu zaman 1 ile düzleştirmek için gerek - yerine ;/ile F)

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

Çevrimiçi deneyin!

Nasıl?

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
;/ile değiştirilebilir F.
Dennis,

2

PHP, 116 Bayt

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

Çevrimiçi sürüm

PHP, 117 Bayt

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

Çevrimiçi deneyin!

PHP, 120 Bayt

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;

Çevrimiçi deneyin!

veya

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 #], 249 245 bayt

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

Çevrimiçi deneyin!

Not: tio.run'daki sürümün başlığında "açık Sistem" var, sayımını yukarıdaki koda ekledim. İthalatta kuralların ne olduğundan emin değilim.

Ungolfed

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 # ile aynı ise , using System;o zaman evet sayıma dahil etmeniz gerekir. F # 'da yapabilirseniz System, ne için olduğunu tam olarak niteleyebilirsiniz . Örneğin, System.Console...yerine C #using System;Console...
TheLethalCoder

@TheLethalCoder Aynı, evet. Ayrıca, bunu açıklığa kavuşturduğun için teşekkürler :) "Aç .." versiyonunu seçtim, çünkü sadece String değil, aynı zamanda bu isim alanında yaşayanları dönüştür.
Brunner


0

J , 34 bayt

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

Çevrimiçi deneyin!

açıklama

[:+/@(,#.;.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

mathematica 193 bayt

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)&

Sen yaparak 7 bayt kaydedebilir f=FromDigits;l=Flatten;başında ve daha sonra olanlar iki fonksiyonların tüm örneklerini değiştirilmesi fve l.
numbermaniac

0

J , 40 bayt

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

kullanımı:

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

44 döndürür


0

Clojure, 150 bayt

#(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'den byte'a dönüşümün bundan daha kısa olmasını umuyordum. Gerçek döngü gövdesi, rmevcut sonucu elde Retmek ve toplam sonucu toplamak için oldukça kısadır . Eğer önceki bit pise 0ve şimdiki bit cise 1o zaman yeni bir öbek ayırır ve biriktiririz R, aksi takdirde günceller rve Rolduğu gibi kalırız .


0

Python 123 bayt

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 sayesinde güncellendi.


1
PPCG'ye Hoşgeldiniz! Tüm cevapların tam programlar veya çağrılabilir işlevler olması gerekir (girişin bir kodlanmış değişkende saklandığı snippet'lerin tersine). Fonksiyon isimlendirilmemiş olabilir, bu yüzden bir lambda w:cevap vermek cevabınızı geçerli kılmak için yeterli olacaktır.
Martin Ender

Üzgünüm, muhtemelen o kadar iyi ifade etmedim. Düzenlemeniz hala geçersiz çünkü a) giriş kodlanmış, b) Bu tam bir programsa, sonucu gerçekten yazdırmıyor. Tam bir program için girişi standart girdiden veya bir komut satırı argümanından okumanız ve sonucu standart çıktıya yazdırmanız gerekir. Bu nedenle, ekleyerek bir işlev olarak göndermenizin en kolay olabileceğini söyledim lambda w:.
Martin Ender

Ohhh, Tamam, anladım, bu yeterli olacaktır: f = lambda w: sum (harita (lambda x: int (x, 2), "". Join (harita (lambda x: bin (ord (x)) ) [2:] .z dolgu (7), liste (w))). ("01", "0: 1") değiştirin. Split (":")))
ShadowCat

evet, bu geçerli. Buna gerek yok f=çünkü isimsiz işlevlere izin veriyoruz (özyinelemeli çağrılar için işlev adına başvurmadığınız sürece).
Martin Ender

0

K (oK) , 31 bayt

Çözüm:

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

Çevrimiçi deneyin!

Örnekler:

+/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

Açıklama:

ASCII değerlerine dönüştürün, 7 bit ikiliye dönüştürün, düzeltin, farklılıkları bulun ve orijinallerin 1farklı olduklarını bulmak için orijinal listesine karşı . Bu indeksleri kesin, ondalık basamağa dönüştürün ve toplayın:

+/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

Bonus

K4'te 31 baytlık bir sürümü de yönetti , ancak TIO olmadığı için OK çözümüm var.

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

0

APL (Dyalog) , 30 bayt

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

Çevrimiçi deneyin!

Nasıl?

⎕UCS⍵ - Unicodify

2⊥⍣¯1¨ - her birini ikili olarak kodlayın

¯7↑¨ - ve 7 yere sıfırlarla sola doğru kaydırın

- yassılaştırmak

1∘+⊆⊢ - kendi kendine bölünme birer birer arttı

2⊥¨ - her birinin ikili kodunun kodunu çözme

+/ - toplam

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.