Calculer le poids de hamming avec un poids de hamming faible

19

Créez un programme qui calcule le poids de hamming d'une chaîne. Winner est le programme avec le poids le plus faible.

Règles:

  • Le poids de Hamming pour un caractère ASCII est défini comme le nombre total de bits définis 1dans sa représentation binaire.
  • Supposons que le codage d'entrée est ASCII 7 bits, transmis via le mécanisme d'entrée normal pour votre langue (par exemple stdin, args, etc.)
  • Exportez le résultat, sous forme de nombre, vers stdout ou tout autre mécanisme de sortie par défaut / normal utilisé par votre langue.
  • Cela devrait aller de soi, mais vous devez être en mesure d' exécuter le programme, dans la vraie vie, pour qu'il soit une solution valide.
  • Winner est la solution dont le code a le poids le plus faible.
  • Désolé, aucune solution en blanc pour celui-ci! Ok, vous pouvez coder en espace maintenant j'ai trié les règles :)

Exemples par caractère:

char |  binary  | weight
-----+----------+-------
a    | 01100001 | 3
x    | 01111000 | 4
?    | 00111111 | 6
\x00 | 00000000 | 0
\x7F | 01111111 | 7
Polynôme
la source
si nous prenons 0x20/ ASCII 32 comme référence, le poids du bourdonnement n'est-il pas de hello world10 plutôt que de 11?
Cristian Lupascu
Pourquoi le poids de hello world11? Seuls 10 caractères sont différents d'un espace. Aussi - le poids de Hamming d'un programme semble être juste sa longueur, à l'exclusion des espaces. Pas si différent du golf à code normal.
ugoren
Désolé, j'ai complètement foiré ça. L'article sur le poids de Wikipédia est assez trompeur, et j'ai totalement foué les règles. Réécriture maintenant. Mise à jour: Ok, réécrit pour le définir comme le nombre de bits mis à 1 dans la chaîne ASCII, désolé pour le bousillage.
Polynôme
@ugoren Une solution avec des caractères ASCII de valeur inférieure a un poids de hamming inférieur.
Polynôme
1
Maintenant, tout cela a du sens. UTILISEZ MAJUSCULE, PRENEZ GARDE ~ET o.
ugoren

Réponses:

6

J (33)

Un de moins de 34!

+/,#:3 u:

Fortement inspiré par cette réponse , mais un poids inférieur à un.

   +/,#:3 u:'+/,#:3 u:'
33
ɐɔıʇǝɥʇuʎs
la source
8

J, poids 34

+/,#:a.i.

Utilisation - placez la chaîne à mesurer entre guillemets à la fin:

   +/,#:a.i.'+/,#:a.i.'
34

Alternativement, en prenant l'entrée du clavier (poids 54):

   +/,#:a.i.1!:1[1
hello
21
Gareth
la source
Il n'y a qu'une seule façon d'écrire ceci :)
éphémère
Il n'y en a pas ... J'ai trouvé une solution qui a un poids inférieur de un.
ɐɔıʇǝɥʇuʎs
N'essayant pas d'être un buzzkill, mais les règles demandent un programme, pas un fragment.
FUZxxl
5

J , 39

+/,#:a.i:]

Il s'agit d'une fonction prenant un argument. (Ou remplacez- ]le directement par la chaîne; comme le note Gareth, cela réduit le coût à 34.)

   + /, #: ai:] 'bonjour le monde'
45
   + /, #: ai:] '+ /, #: ai:]'
39
éphémère
la source
Les grands esprits se rencontrent. :-)
Gareth
5

Python, 189

print sum(bin(ord(A)).count("1")for A in raw_input())
Keith Randall
la source
2
L'équivalent Python 3 print(sum(bin(ord(A)).count('1')for A in input())), a un score de 180.
dan04
4
@ dan04: Utilisez des guillemets doubles au lieu de simples pour 176.
Keith Randall
5

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

Le bon outil pour le travail, ça craint toujours bien sûr.

a cessé de tourner dans le sens antihoraire
la source
1
+1 pour avoir utilisé l'une de mes langues préférées de tous les temps. C'est la première langue que j'ai apprise à coder sur un PC.
Polynôme
5

Unaire 0

Vous saviez tous que ça allait arriver. Tout d'abord le programme BrainFuck:

,[[>++[>>+>+<<<-]>>>
[<<<+>>>-]>>[-]<<<<<<[>>>>+>>+<<<<<<-]>>>>>>
[<<<<<<+>>>>>>-]<<<[>>+>+<<<-]>>>[<<<+>>>-]
[-]<<[>>[-]<[>[-]+<[-]]<[-]]>[-]>[<<<<<<->>>->>>
[-]<<<<<<[>>>>+>>+<<<<<<-]>>>>>>[<<<<<<+>>>>>>-]<<<
[>>+>+<<<-]>>>[<<<+>>>-][-]<<[>>[-]<[>[-]+<[-]]<[-]]>[-]>]<<<<<<
[>>+<[>>+>+<<<-]>>>[<<<+>>>-]>>[-]<<<<<<[>>>>+>>+<<<<<<-]>>>>>>
[<<<<<<+>>>>>>-]<<<[>>+>+<<<-]>>>[<<<+>>>-][-]<<[>>[-]<[>[-]+<[-]]<[-]]> 
[-]>[<<<<<<->>>->>>[-]<<<<<<[>>>>+>>+<<<<<<-]>>>>>>[<<<<<<+>>>>>>-]<<<
[>>+>+<<<-]>>>[<<<+>>>-][-]<<[>>[-]<[>[-]+<[-]]<[-]]>[-]>]<<<<<<]>>>
[>+>+<<-]>>[<<+>>-][-]+<[>[-]<<[<<->>-]<<[>>+<<-]>>>[-]]>[<<<+<[-]>>>>
[-]]<<[->>>>+<<<<]<[-<<+>>]<<],]>>>>>>>.

J'ai ajouté des nouvelles lignes pour le rendre "lisible" mais il a un poids de Hamming de 4066. Il fonctionne en obtenant à plusieurs reprises le quotient / les restes d'une chaîne d'entrée et en additionnant tous les restes. Bien sûr, si vous l'exécutez sur lui-même, vous obtenez: 226 (4066% 256) (techniquement \ xe2) si clairement qu'il se déclare vainqueur.

Maintenant, nous le convertissons en Unary et obtenons

000 ... 9*google^5.9 0's ... 000

Nous utilisons une implémentation unaire avec des caractères NULL \ x00 pour '0' et boom, ce qui entrave le poids de 0.

Question bonus : pour quels caractères ASCII cpouvez-vous exécuter ce programme sur une chaîne composée de Nrépétitions et le faire sortir ce caractère. (EG une chaîne de 32 espaces donne un espace). Quelles valeurs du Ntravail (soit un nombre infini d'entre elles fonctionnera, soit aucune ne fonctionnera).

walpen
la source
1
Je ne suis pas sûr de comprendre cette solution. Le programme de brainfuck a un poids énorme. Unary accepte-t-il des octets nuls en tant que programme, ou auriez-vous besoin de réimplémenter Unary? Si c'est le dernier, ce n'est pas vraiment une solution valable - n'importe qui pourrait simplement dire "Je définis un langage de programmation où n'importe quel octet d'entrée unique donne {résultat}", et gagner chaque défi de golf de code sur le site.
Polynôme
1
Un caractère nul Unary serait bien. Tout ce dont vous avez besoin est un EOF pour dire d'arrêter de compter. En fait, voici un pseudo-C pour lire ce fichier: main(){ bignum Unarynum = 0; int c; while(EOF!=(c=readchar())){ Unarynum++; } return Unarynum; }Peu importe ce que vous choisissez d'être votre personnage Unary (tant qu'il n'est pas EOF).
walpen
1
Eh bien, voici un compilateur unaire au C qui fonctionne très bien avec des caractères nuls: ideone.com/MIvAg . Bien sûr, le fichier requis pour faire ce programme ne rentrerait pas dans l'univers, mais nous avons la capacité de l'exécuter.
walpen
3
Si vous ne pouvez pas réellement l' exécuter, ce n'est pas vraiment une solution.
Polynôme
4
Comme Carl Sagan l' a dit un jour: "Si vous souhaitez calculer le poids de hamming d'une corde, vous devez d'abord inventer 10 ^ 500 univers." (milliards et milliards, même)
walpen
4

C, poids 322 263 256

Le poids du hamming est-il important?

main(D,H,A)char*A,**H;{for(A=*++H;*A;A+=!(*A/=2))D+=*A%2;printf("%d",D-2);}

Utilisé principalement des techniques de golf standard.
Une seule boucle calcule le poids (décalage vers la droite et ajout jusqu'à zéro) et analyse la chaîne (avance le pointeur lorsque le zéro est atteint).
En supposant Dest initialisé à 2 (paramètre unique).

Optimisations spécifiques au poids de Hamming:
1. ABDH, avec un poids de 2 chacun, utilisé pour les noms.
2. *++Hpréféré à H[1].

ugoren
la source
Hah, je n'ai absolument pas compris votre première phrase jusqu'à maintenant.
boîte à pain le
Vous pouvez obtenir le score à 230 en sortant le résultat sous la forme d' un nombre unaire :main(D,H,A)char*A,**H;{for(A=*++H;*A;A+=!(*A/=2))if(*A%2)printf("@");}
schnaader
@schnaader, je n'ai jamais su qu'il y @avait un chiffre dans le système unaire. Je pensais qu'il n'utilisait que 0..0 . Mais si vous voulez y aller, printf("@"+*a%2)c'est plus court.
ugoren
@ugoren: dépend de la convention / définition d'unaire. Par exemple en.wikipedia.org/wiki/Unary_numeral_system utilise des marques de pointage et dit "Il n'y a pas de symbole explicite représentant zéro en unaire comme il en existe dans d'autres bases traditionnelles".
schnaader
@schnaader, OK, mais je pense que cela pousse trop loin l'exigence "en nombre".
ugoren
4

Golfscript 84 72 58

{2base~}%{+}*

(merci à Howard et Peter Taylor pour leur aide)

Entrée: la chaîne d'entrée doit être sur la pile (passée comme argument de ligne de commande, ou simplement placée sur la pile).

Si vous l'exécutez à partir de la ligne de commande, assurez-vous de l'utiliser echo -n, sinon la nouvelle ligne de fin sera également comptée.

Sortie: imprime la valeur du poids de freinage sur la console

Le programme peut être testé ici .

Cristian Lupascu
la source
1
Est-ce que Golfscript est sensible à la casse? Sinon, vous pouvez enregistrer quelques bits en utilisant BASEau lieu de base. Mise à jour: juste vérifié, BASEne fonctionne pas. Bonne solution :)
Polynomial
@Polynomial J'ai essayé cela après avoir vu votre TEST/ testcommentaire :) Mais cela ne fonctionne pas.
Cristian Lupascu
Vous pouvez vous en débarrasser {...}2*en postulant 2base~en premier lieu. Obtient le score à 72.
Howard
@Howard merci pour ce bon conseil! Je l'ai appliqué dans ma réponse.
Cristian Lupascu
Votre mécanisme de test est incorrect, car vous avez oublié une limitation importante de votre page Web GolfScript. Vous devriez avoir un ;avant la chaîne que vous remplacez par stdin, donc ce (;n'est pas nécessaire. Puis l'observation de Howard le ramène à 65.
Peter Taylor
2

Perl, 80 (22 caractères)

Fait et fait:

perl -0777nE 'say unpack"%32B*"'

Ou voici une version alternative avec un poids de 77 (21 caractères):

perl -0777pE '$_=unpack"%32B*"'

Je n'aime pas autant cette version, car sa sortie omet la dernière ligne.

Pour calculer le poids, je suppose que je compte les caractères de la manière habituelle (à l'exclusion du perl -e/ -E, mais en incluant d'autres caractères d'option). Si, pour une raison quelconque, les gens se plaignent de cela, le mieux que je puisse faire sans options est de 90 (26 caractères):

$/=$,,say unpack"%32B*",<>

Exemple d'utilisation:

$ perl -0777nE 'say unpack"%32b*"' rickroll.txt
7071

Boom.

boite à pain
la source
2

Pyth - 15

Avertissement: Cette réponse n'est pas éligible pour gagner car Pyth est plus jeune que ce défi.

Utilise .Bla représentation binaire et compte le nombre de "1".

/.BQ\1

Prend l'entrée dans une chaîne pour enregistrer par zrapport à Q.

Essayez-le en ligne ici .

Maltysen
la source
1

Scala 231

readLine().map(_.toInt.toBinaryString).flatten.map(_.toInt-48)sum

Code d'autotest:

"""readLine().map(_.toInt.toBinaryString).flatten.map(_.toInt-48)sum""".map(_.toInt.toBinaryString).flatten.map(_.toInt-48)sum

avec modification d'auto-test.

Utilisateur inconnu
la source
C'est le poids 495, pas 231. Vous ne pouvez pas obtenir le poids 231 avec 126 caractères - c'est une moyenne de moins de 2, et tous les caractères imprimables (sauf @et l'espace, que vous n'utilisez pas) ont un poids 2 au moins.
ugoren
1
@ugoren: Mais ce n'est que 65 caractères. Le programme est imprimé près de deux fois: une fois le code pour calculer le poids du hamming, et une deuxième fois comme entrée statique pour le calculer pour le programme. Mais la partie calculatrice manque la "readLine ()" en face, car elle prend l'entrée littérale. J'ai essayé de clarifier la réponse elle-même.
utilisateur inconnu
1

Java, poids 931 774 499 454

Je pense que c'est la seule réponse pour le moment avec un poids supérieur à 300 environ.

class H{public static void main(String[]A){System.out.print(new java.math.BigInteger(A[0].getBytes()).bitCount());}}

Attend l'entrée comme argument de ligne de commande.

SuperJedi224
la source
1

GNOU sed -r , 467 + 1

(+1 pour l'utilisation de -r- ou cela devrait-il être +4?)

Sorties sous forme de valeur unaire par ligne source; pour convertir en un total décimal, redirigez la sortie vers | tr -d "\n" | wc -c. Compte tous les caractères ASCII imprimables (32-126), plus le saut de ligne (10).

s@[a-z]@\U& @g
s@[?{}~]@      @g
s@[][/7;=>OW|^]@     @g
s@[-'+.3569:<GKMNSUVYZ\\]@    @g
s@[#%&)*,CEFIJL1248ORTX]@   @g
s@$|[!"$(ABDH0P`]@  @g
y! @!11!

Il est difficile d'éviter de lister tous les caractères, mais nous pouvons réduire cela en observant que les lettres minuscules ont un poids de Hamming supérieur à celui des lettres majuscules correspondantes. Nous préférons la nouvelle ligne (score 2) au point-virgule (score 5) comme séparateur d'instructions; nous préférons @(score 1) ou !(score 2) à/ (score 5) comme délimiteur de modèle.

Remarque - pour obtenir les bons jeux de caractères, j'ai créé ce tableau à partir de celui de man ascii, trié par poids. Ajoutez simplement les scores à droite et en dessous pour obtenir le poids global de chaque personnage:

   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

Cela pourrait s'avérer utile à d'autres.

Toby Speight
la source
0

Julia 262 268

La version modifiée utilise la fonction pratique 'count_ones' pour une économie de 6 (262)

show(mapreduce(x->count_ones(x),+,map(x->int(x),collect(ARGS[1]))))

Ancienne version sans fonction de comptage intégrée (268)

show(mapreduce(x->int(x)-48,+,mapreduce(x->bits(x),*,collect(ARGS[1]))))

Utilise l'argument de ligne de commande pour l'entrée.

Bakerg
la source
0

CJam 52 ou 48

Si l'entrée n'est pas déjà sur la pile (52)

q:i2fbs:s:i:+

Si l'entrée est sur la pile (48)

:i2fbs:s:i:+

Par exemple

"Hello World":i2fbs:s:i:+
Bakerg
la source
0

Julia, HW 199

H=mapreduce;H(B->B=='1',+,H(P->bits(P),*,collect(A[:])))

Avec

A="H=mapreduce;H(B->B=='1',+,H(P->bits(P),*,collect(A[:])))"

ou en insérant directement la chaîne:

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

La version non golfée (HW 411) ressemble à ceci:

bitstring=mapreduce(x->bits(x),*,collect(teststring[:]))
mapreduce(checkbit->checkbit=='1',+,bitstring)

Et pour le plaisir, voici une version optimisée (Hamming Weight 231 ) du point de vue de Bakerg sur le problème:

A=mapreduce;show(A(B->int(B)-48,+,A(B->bits(B),*,collect(H[:]))))

avec

H="A=mapreduce;show(A(B->int(B)-48,+,A(B->bits(B),*,collect(H[:]))))"
ML
la source
0

HPPPL (langage de programmation HP Prime), 74

sum(hamdist(ASC(a),0))

La calculatrice graphique HP Prime a une fonction hamdist () intégrée. Le poids de hamming de chaque personnage est le même que la distance de hamming de 0.

ASC (chaîne) crée un tableau des valeurs ASCII de chaque caractère d'une chaîne.

hamdist (valeur, 0) calcule la distance de hamming à partir de 0 pour chaque valeur ASCII

sum () résume toutes les valeurs.

Calcul du poids du hamming de son propre code source:

Hamming Weight HPPPL

ML
la source
0

05AB1E , poids 17 (4 octets )

ÇbSO

Essayez-le en ligne ou vérifiez d'autres cas de test .

Explication:

Ç       # 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
Kevin Cruijssen
la source
0

Perl 6 , 102

+*.ords>>.base(2).comb(~1)

Essayez-le en ligne!

Bien que ce ne soit pas du golf de code, la solution la plus courte semble également avoir le plus petit poids de hamming ...

Jo King
la source