Opret et program, der beregner hammingvægt af en streng. Vinderen er det program, der har den laveste hammingvægt.
Regler:
- Hammingvægt for et ASCII-tegn defineres som det samlede antal bits indstillet til
1
i sin binære repræsentation. - Antag, at inputkodning er 7-bit ASCII, ført gennem den inputmekanisme, der er normal for dit sprog (f.eks. Stdin, args osv.)
- Output resultatet, som et tal, til stdout eller hvilken som helst standard / normal outputmekanisme, dit sprog bruger.
- Det burde være en selvfølge, men du skal være i stand til faktisk at køre programmet i det virkelige liv for at det skal være en gyldig løsning.
- Vinder er den løsning, hvis kode har den laveste hammingvægt.
-
Undskyld, ingen løsninger i whitespace til denne!Ok, du kan kode i whitespace nu har jeg ordnet reglerne 🙂
Eksempler pr. tegn:
char | binary | weight -----+----------+------- a | 01100001 | 3 x | 01111000 | 4 ? | 00111111 | 6 \x00 | 00000000 | 0 \x7F | 01111111 | 7
Kommentarer
Svar
J (33)
En lavere end 34!
+/,#:3 u:
Tungt inspireret af dette svar , men en hammingvægt på en lavere.
+/,#:3 u:"+/,#:3 u:" 33
Svar
J, vægt 34
+/,#:a.i.
Brug – placer streng, der skal måles med anførselstegn i slutningen:
+/,#:a.i."+/,#:a.i." 34
Alternativt kan du tage input fra tastaturet (vægt 54):
+/,#:a.i.1!:1[1 hello 21
Kommentarer
- Der er ‘ kun en måde at skrive dette på:)
- Der er ikke ‘ t … Jeg fandt en løsning, der har en hammingvægt på en lavere.
- Ikke forsøger at være en buzzkill, men reglerne beder om et program, ikke et fragment.
Svar
J , 39
+/,#:a.i:]
Dette er en funktion, der tager en argument. (Eller udskift ]
med strengen direkte; som Gareth bemærker, det bringer omkostningerne ned til 34.)
+/,#:a.i:] "hello world" 45 +/,#:a.i:] "+/,#:a.i:]" 39
Kommentarer
- Store sind tænker ens. 🙂
Svar
Python, 189
print sum(bin(ord(A)).count("1")for A in raw_input())
Kommentarer
- Python 3-ækvivalenten,
print(sum(bin(ord(A)).count('1')for A in input()))
, har en score på 180. - @ dan04: Brug dobbelt anførselstegn i stedet for enkelt for 176.
Svar
QBasic, 322 311 286 264
H$=COMMAND$ FOR A=1 TO LEN(H$) B=ASC(MID$(H$,A,1)) WHILE B>0 D=D+B MOD 2 B=B\2 WEND NEXT ?D
Type det rigtige værktøj til jobbet, suger selvfølgelig stadig.
Kommentarer
- +1 for at bruge et af mine yndlingssprog nogensinde. Det ‘ er det første sprog, jeg lærte at kode ind på en pc.
Svar
Unary 0
I vidste alle, at det ville komme. Først BrainFuck-programmet:
,[[>++[>>+>+<<<-]>>> [<<<+>>>-]>>[-]<<<<<<[>>>>+>>+<<<<<<-]>>>>>> [<<<<<<+>>>>>>-]<<<[>>+>+<<<-]>>>[<<<+>>>-] [-]<<[>>[-]<[>[-]+<[-]]<[-]]>[-]>[<<<<<<->>>->>> [-]<<<<<<[>>>>+>>+<<<<<<-]>>>>>>[<<<<<<+>>>>>>-]<<< [>>+>+<<<-]>>>[<<<+>>>-][-]<<[>>[-]<[>[-]+<[-]]<[-]]>[-]>]<<<<<< [>>+<[>>+>+<<<-]>>>[<<<+>>>-]>>[-]<<<<<<[>>>>+>>+<<<<<<-]>>>>>> [<<<<<<+>>>>>>-]<<<[>>+>+<<<-]>>>[<<<+>>>-][-]<<[>>[-]<[>[-]+<[-]]<[-]]> [-]>[<<<<<<->>>->>>[-]<<<<<<[>>>>+>>+<<<<<<-]>>>>>>[<<<<<<+>>>>>>-]<<< [>>+>+<<<-]>>>[<<<+>>>-][-]<<[>>[-]<[>[-]+<[-]]<[-]]>[-]>]<<<<<<]>>> [>+>+<<-]>>[<<+>>-][-]+<[>[-]<<[<<->>-]<<[>>+<<-]>>>[-]]>[<<<+<[-]>>>> [-]]<<[->>>>+<<<<]<[-<<+>>]<<],]>>>>>>>.
Jeg tilføjede nye linjer for at gøre det “læsbart”, men det har en Hamming-vægt på 4066. Det fungerer ved gentagne gange at få kvotienten / resterne af en inputstreng og tilføje alle de resterende. Selvfølgelig, hvis du kører det på sig selv, får du: 226 (4066% 256) (teknisk \ xe2) så klart, at det regerer sig selv vinderen.
Nu konverterer vi det til Unary og får
000 ... 9*google^5.9 0"s ... 000
Vi bruger en unormal implementering med NULL-tegn \ x00 til “0” og boom, hammingvægt på 0.
Bonusspørgsmål : For hvilke ASCII-tegn c
kan du køre dette program på en streng bestående af N
gentagelser og få det til at udskrive det tegn. (F.eks. Giver en streng på 32 mellemrum et mellemrum).Hvilke værdier af N
fungerer (enten fungerer et uendeligt antal af dem, eller ingen fungerer).
Kommentarer
- Jeg ‘ er ikke sikker på, at jeg forstår denne løsning. Brainfuck-programmet har en enorm hammingvægt. Accepterer Unary null bytes som et program, eller skal du genimplementere Unary? Hvis det ‘ er sidstnævnte, er det ‘ ikke rigtig en gyldig løsning – nogen kunne bare sige ” Jeg definerer et programmeringssprog, hvor en enkelt input-byte giver {resultat} “, og vinder hver kode golfudfordring på webstedet.
- En null karakter Unary ville være fint. Alt hvad du behøver er en EOF til at sige stop med at tælle. Faktisk her er ‘ noget pseudo-C for at læse den fil:
main(){ bignum Unarynum = 0; int c; while(EOF!=(c=readchar())){ Unarynum++; } return Unarynum; }
Er det ikke ‘ Det betyder overhovedet ikke, hvad du vælger at være din unary char (så længe det ikke er ‘ t EOF). - Nå her ‘ er uenig i forhold til C-kompilatoren, der fungerer fint med nul tegn: ideone.com/MIvAg . Naturligvis ville den fil, der kræves for at lave dette program, ikke passe i universet, men vi har kapacitet til at køre det.
- Hvis du kan ‘ t faktisk kør det, det ‘ er ikke rigtig en løsning.
- Som Carl Sagan sagde engang: ” Hvis du ønsker at beregne en strenges hammingvægt, skal du først opfinde 10 ^ 500 universer. ” (milliarder og milliarder, lige)
Svar
C, vægt 322 263 256
Tæller hammingvægtens hammevægt?
main(D,H,A)char*A,**H;{for(A=*++H;*A;A+=!(*A/=2))D+=*A%2;printf("%d",D-2);}
Brugte mest almindelig golf teknikker.
En enkelt sløjfe beregner vægten (skifter til højre og tilføjer indtil nul) og scanner strengen (bevæger markøren, når nul er nået).
Antages D
initialiseres til 2 (enkelt parameter).
Hamming vægt specifikt optimizati ons:
1. ABDH
med vægt 2 hver, brugt til navne.
2. *++H
foretrukket frem for H[1]
.
Kommentarer
- Hah, jeg forstod fuldstændigt din første sætning indtil lige nu.
- Du kan få scoren ned til 230 ved at udlæse resultatet som et unary nummer:
main(D,H,A)char*A,**H;{for(A=*++H;*A;A+=!(*A/=2))if(*A%2)printf("@");}
- @schnaader , Jeg vidste aldrig, at
@
var et tal i det unary system. Jeg troede, det kun bruger0
..0
. Men hvis du vil gå denne vej, erprintf("@"+*a%2)
kortere. - @ugoren: Afhænger af konventionen / definitionen af unary. For eksempel. da.wikipedia.org/wiki/Unary_numeral_system bruger stemmemarkeringer og siger ” Der er intet eksplicit symbol, der repræsenterer nul på samme måde som i andre traditionelle baser “.
- @schnaader, OK, men jeg tror det ‘ s strækker kravet ” som et tal ” for langt.
Svar
Golfscript 84 72 58
{2base~}%{+}*
(tak til Howard og Peter Taylor for deres hjælp)
Input: inputstrengen skal være på stakken (bestået som kommandolinje argument eller blot placeres på stakken).
Hvis du kører det fra kommandolinjen, skal du sørge for at bruge echo -n
, ellers vil den bageste nye linje også tælles.
Output: udskriver hamming-vægtværdien til konsollen
Programmet kan testes
her .
Kommentarer
- Er Golfscript store og små bogstaver? Hvis ikke, kan du gemme et par bits ved at bruge
BASE
i stedet forbase
. Opdatering: Bare markeret,BASE
fungerer ikke ‘. God løsning 🙂 - @ Polynomial Jeg prøvede det efter at have set din
TEST
/test
kommentar 🙂 Men det gør det ikke ‘ fungerer ikke. - Du kan slippe af med
{...}2*
ved at anvende2base~
i første omgang. Får point ned til 72. - @Howard tak for dette gode tip! Jeg ‘ har anvendt det i mit svar.
- Din testmekanisme er forkert, fordi du ‘ har glemt en vigtig begrænsning af din Web GolfScript-side. Du skal have en
;
foran den streng, som du erstatter stdin, så(;
er unødvendig. Derefter får Howard ‘ s observation ned til 65.
Svar
Perl, 80 (22 tegn)
Udført og færdig:
perl -0777nE "say unpack"%32B*""
Eller her er en alternativ version med en vægt på 77 (21 tegn):
perl -0777pE "$_=unpack"%32B*""
Jeg kan ikke lide den version så meget, fordi dens output udelader den endelige nye linje.
For at beregne vægten antager jeg, at jeg tæller tegn på den sædvanlige måde (eksklusive perl -e
/ -E
, men inklusive andre valgtegn). Hvis folk af en eller anden grund klager over dette, er det bedste, jeg kan gøre uden muligheder, 90 (26 tegn):
$/=$,,say unpack"%32B*",<>
Eksempel på brug:
$ perl -0777nE "say unpack"%32b*"" rickroll.txt 7071
Bom.
Svar
Pyth – 15
Ansvarsfraskrivelse: Dette svar er ikke berettiget til at vinde, da Pyth er yngre end denne udfordring.
Bruger .B
til binær repræsentation og tæller antallet af "1"
“s.
/.BQ\1
Tager input i en streng for at gemme på z
versus Q
.
Svar
Scala 231
readLine().map(_.toInt.toBinaryString).flatten.map(_.toInt-48)sum
Selftesting-kode:
"""readLine().map(_.toInt.toBinaryString).flatten.map(_.toInt-48)sum""".map(_.toInt.toBinaryString).flatten.map(_.toInt-48)sum
med selvtestændring.
Kommentarer
- Det ‘ s vægt 495, ikke 231. Du kan ‘ t få vægt 231 med 126 tegn – at ‘ er et gennemsnit på mindre end 2 og alle tegn, der kan udskrives (undtagen
@
og mellemrum, som du ikke ‘ t brug) har mindst 2 vægt. - @ugoren: Men det er ‘ kun 65 tegn. Programmet udskrives næsten to gange: En gang koden til beregning af hammingvægten og en anden gang som statisk input for at beregne den til programmet. Men den beregnende del mangler ” readLine () ” foran, fordi det tager den bogstavelige input. Jeg forsøgte at afklare selve svaret.
Svar
Java, vægt 931 774 499 454
Jeg tror, det er det eneste svar i øjeblikket med en vægt på over 300.
class H{public static void main(String[]A){System.out.print(new java.math.BigInteger(A[0].getBytes()).bitCount());}}
Forventer input som kommandolinjeargument.
Svar
GNU sed -r
, 467 + 1
(+1 til brug af -r
– eller skal det være +4?)
Udgives som en unary værdi pr. kildelinje; for at konvertere til et decimaltotal omdirigerer output til | tr -d "\n" | wc -c
. Tæller alle udskrivbare ASCII-tegn (32-126) plus linefeed (10).
s@[a-z]@\U& @g s@[?{}~]@ @g s@[][/7;=>OW|^]@ @g s@[-"+.3569:<GKMNSUVYZ\\]@ @g s@[#%&)*,CEFIJL1248ORTX]@ @g s@$|[!"$(ABDH0P`]@ @g y! @!11!
Det er svært at undgå at liste alle tegn, men vi kan reducere dette observerer, at små bogstaver har en Hamming-vægt på en mere end de tilsvarende store bogstaver. Vi foretrækker newline (score 2) frem for semikolon (score 5) som en sætningsadskiller, vi foretrækker @
(score 1) eller !
(score 2) over /
(score 5) som mønsterafgrænser.
Bemærk – for at få de rigtige sæt af tegn oprettede jeg denne tabel ud fra den i man ascii
, sorteret efter vægt. Bare tilføj scoringerne til højre og nedenfor for at få den samlede vægt af hvert tegn:
2 4 3 5 6 7 --- ------ - 0: @ 0 P ` p |0 1: ! A 1 Q a q | 2: " B 2 R b r |1 4: $ D 4 T d t | 8: ( H 8 X h x | 3: # C 3 S c s | 5: % E 5 U e u | 6: & F 6 V f v |2 9: ) I 9 Y i y | A: * J : Z j z | C: , L < \ l | | 7: ´ G 7 W g w | B: + K ; [ k { |3 D: - M = ] m } | E: . N > ^ n ~ | F: / O ? _ o |4 --- ------ - 1 2 3
Dette kan vise sig nyttigt for andre.
Svar
Julia 262 268
Modificeret version bruger praktisk “count_ones” -funktion til en besparelse på 6 (262)
show(mapreduce(x->count_ones(x),+,map(x->int(x),collect(ARGS[1]))))
Gammel version uden brug af en indbygget en-tællefunktion (268)
show(mapreduce(x->int(x)-48,+,mapreduce(x->bits(x),*,collect(ARGS[1]))))
Bruger kommandolinjeargument til input.
Svar
CJam 52 eller 48
Hvis input ikke allerede er på stakken (52)
q:i2fbs:s:i:+
Hvis input er på stack (48)
:i2fbs:s:i:+
For eksempel
"Hello World":i2fbs:s:i:+
Svar
Julia, HW 199
H=mapreduce;H(B->B=="1",+,H(P->bits(P),*,collect(A[:])))
Med
A="H=mapreduce;H(B->B=="1",+,H(P->bits(P),*,collect(A[:])))"
eller ved direkte at indsætte strengen:
julia> H=mapreduce;H(B->B=="1",+,H(P->bits(P),*,collect("H=mapreduce;H(B->B=="1",+,H(P->bits(P),*,collect(A[:])))"))) 199
Den ugolfede version (HW 411) ser sådan ud:
bitstring=mapreduce(x->bits(x),*,collect(teststring[:])) mapreduce(checkbit->checkbit=="1",+,bitstring)
Og til sjov for det er her en optimeret version (Hamming Weight 231 ) af bakerg tager problemet op:
A=mapreduce;show(A(B->int(B)-48,+,A(B->bits(B),*,collect(H[:]))))
med
H="A=mapreduce;show(A(B->int(B)-48,+,A(B->bits(B),*,collect(H[:]))))"
Svar
HPPPL (HP Prime Programming Language), 74
sum(hamdist(ASC(a),0))
HP Prime-grafregner har en indbygget hamdist-funktion ().Hammingsvægten for hvert tegn er den samme som hammingsafstanden fra 0.
ASC (streng) skaber en matrix med ASCII-værdierne for hvert tegn i en streng.
hamdist ( værdi, 0) beregner hammingafstanden fra 0 for hver ASCII-værdi
sum () opsummerer alle værdier.
Beregning af hammingvægt for sin egen kildekode:
Svar
05AB1E , vægt 17 (4 byte )
ÇbSO
Prøv det online eller kontrollere nogle flere testtilfælde .
Forklaring:
Ç # Convert the characters in the (implicit) input to their ASCII decimal values # i.e. "Test" → [84,101,115,116] b # Convert those values to binary # i.e. [84,101,115,116] → ["1010100","1100101","1110011","1110100"] S # Split it into a list of 0s and 1s (implicitly flattens) # i.e. ["1010100","1100101","1110011","1110100"] # → [1,0,1,0,1,0,0,1,1,0,0,1,0,1,1,1,1,0,0,1,1,1,1,1,0,1,0,0] O # Sum those (and output implicitly) # i.e. [1,0,1,0,1,0,0,1,1,0,0,1,0,1,1,1,1,0,0,1,1,1,1,1,0,1,0,0] → 16
Svar
Perl 6 , 102
+*.ords>>.base(2).comb(~1)
Selvom dette ikke koder golf, synes den korteste løsning også at have den mindste hammingvægt …
0x20
/ ASCII 32 som reference, er ‘ t den brummende vægt afhello world
10 i stedet for 11?hello world
11? Kun 10 tegn adskiller sig fra et mellemrum. Også – et program ‘ s Hamming-vægt synes kun at være dets længde eksklusive mellemrum. Ikke så forskellig fra normal kodegolf.~
OGo
.