Conversion de la base 10 à la base 2 sans conversions de base intégrées

16

Contexte :

Vous avez été chargé de convertir des nombres de base 10 en base 2 sans utiliser de fonctions de conversion de base prédéfinies. Vous ne pouvez pas non plus utiliser de bibliothèques importées.

Problème :

Convertissez une chaîne d'entrée de la base 10 (décimale) en base 2 (binaire). Vous ne pouvez pas utiliser de code / fonctions / méthodes de conversion de base prédéfinies, ni de bibliothèques importées. Puisqu'il s'agit de , la réponse la plus courte en octets gagnera.

L'entrée sera comprise entre -32768 et 32767 (incluez la gestion des octets de signe dans votre code)

Le docteur
la source
3
Q: Que signifie "gestion des octets de signe" - dois-je sortir "-xxxx" pour un nombre négatif? Alors certains d'entre nous ont tort, incl. moi, comme je produis "11 ... 11" pour -1 (alias comme non signé)
blabla999
Gestion des octets de signe - le MSB des variables signées contrôle si elles sont négatives
TheDoctor
1
bien sûr, mais dois-je> les imprimer en signe «-» suivi de la magnitude?
blabla999
@ blabla999 - Non tu ne le fais pas
TheDoctor
3
the MSB of signed variables controls if they are negative- cela ressemble à du bit de signe, mais comme la gamme le -32768..32767suggère, vous voulez un complément à 2. Alors que voulez-vous? ..
mniip

Réponses:

4

GolfScript - 17 octets

~{.1&\2/}16*;]-1%

Pas trop verbeux que le intégré ~2base.

primo
la source
1
Je ne connais pas golfscript mais quelques échantillons m'amènent à conclure que vous devez supprimer le~
user12205
@ace Parce que l'entrée initiale est une chaîne "37", par exemple, l'opération "37" & 1(en infixe) est une opération par ensemble. L' ~avant convertit l'entrée en un entier.
primo
J'ai fait mon test ici golfscript.apphb.com/… cela signifie-t-il que cet interprète est incorrect? (Désolé, je ne sais vraiment rien de golfscript)
user12205
2
L'interprète a raison; car vous avez poussé la valeur entière 10sur la pile, il n'est pas nécessaire de l'évaluer. Cependant, lors de la lecture stdin, l'entrée sera une chaîne ( testez ici ). La description du problème indique également explicitement que l'entrée est une chaîne.
primo
12

JavaScript, 46

for(x=prompt(o='');x;x>>>=1)o=(x&1)+o;alert(o)
copie
la source
Lol, je ne savais même pas qu'un opérateur à 4 caractères ( >>>=) existait! +1 (En outre, si vous l'exécutez dans la console, vous pouvez enregistrer les 9 derniers caractères.)
Poignée de porte
1
Ce n'est pas 4 caractères, ce sont deux opérateurs: le >>> est le décalage à droite au niveau du bit de 0, suivi d'une affectation. Essayez: x=8; x>>>=1; x;et x=8; x>>>1; x;- dans le premier cas, la valeur de x a changé; dans le second, ce n'est pas le cas.
Graham Charles
3
@GrahamCharles >>>=est un opérateur unique .
primo
Eh bien, regardez ça! Merci, @primo ... vous apprenez quelque chose tous les jours!
Graham Charles
2
@ComFreek Cela inverserait l'ordre des chiffres
copie le
4

Brainf * ck, 98 77

Évidemment, ce n'est pas dans le but de gagner, mais que serait une compétition si elle n'avait pas de solution brainfk

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

Étant donné que brainfk ne peut gérer que des entiers 8 bits et aucun négatif, je suppose qu'il ne respecte pas pleinement les règles, mais je n'ai jamais été là pour le gagner.

Cela fonctionne réellement pour une entrée 16 bits si votre interprète prend en charge

Je l'ai même obtenu en sortie en valeurs ascii

Voici le code annoté:

++[>++++<-]                       preload 8 onto cell 1
>>,<                                input into cell 2
[-                                  iterate over cell 1
    >>++<                               put 2 in cell 3
    [->-[>+>>]>[+[-<+>]>+>>]<<<<<]      division algorithm: converts {n d} into {0 d_minus_n%d n%d n/d}
    >[-]++++++[->++++++++<]>           clears cell 4 and puts 48(ascii of 0) into cell 5
    .[-]                                output n%2 and clear it (the bit)
    >[-<<<+>>>]                         bring n/2 into cell 2 (to be used for division in next iteration)
<<<<]                               end iterate

Algorithme plus court (77):

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

Celui-ci ne peut gérer que des entiers 8 bits.

L'algorithme fonctionne en utilisant un compteur binaire qui est en fait très court (un incrément permet de >[->]++[-<+]-<-disposer les bits. Le problème est qu'il est difficile d'imprimer tous les bits

Ce dernier algorithme peut être adapté pour s'adapter à n'importe quel nombre de bits au détriment des octets. Pour pouvoir traiter des entiers N bits, il faut 53 + 3 * N octets pour coder.

exemples:

(1 bit) +>,>-<[>>[->]++[-<+]-<-]++++++++[->++++++<]>+[->+<]>[.>]
(2 bit) +>,>-<[>>[->]++[-<+]-<-]++++++++[->++++++<]>+[->+>+<<]>[.>]
(3 bit) +>,>-<[>>[->]++[-<+]-<-]++++++++[->++++++<]>+[->+>+>+<<<]>[.>]
etc
DEMANDER
la source
3

Réponse APL obligatoire - 21 22

"01"[1+2|⌊⎕÷2⋆⊖0,⍳15]

Exemples:

      "01"[1+2|⌊⎕÷2⋆⊖0,⍳15]
⎕: 0
0000000000000000
      "01"[1+2|⌊⎕÷2⋆⊖0,⍳15]
⎕: 13
0000000000001101
      "01"[1+2|⌊⎕÷2⋆⊖0,⍳15]
⎕: 9999
0010011100001111
      "01"[1+2|⌊⎕÷2⋆⊖0,⍳15]
⎕: -3
1111111111111101
      "01"[1+2|⌊⎕÷2⋆⊖0,⍳15]
⎕: 32767
0111111111111111
mniip
la source
Vous pouvez réduire avec près de 50% en utilisant ⎕IO←0, et retourne un tableau de bits au lieu d'une chaîne: 2|⌊⎕÷2*⊖⍳16.
Adám
3

Code machine de Turing, 272 octets

Comme d'habitude, j'utilise la syntaxe de table de règles définie ici. Vous pouvez le tester sur ce site ou, en variante, en utilisant cette implémentation java.

Une grande partie du code est copiée de mon convertisseur décimal-hexadécimal ici.

0 * * l B
B * * l C
C * 0 r D
D * * r E
E * * r A
A _ * l 1
A * * r *
1 0 9 l 1
1 1 0 l 2
1 2 1 l 2
1 3 2 l 2
1 4 3 l 2
1 5 4 l 2
1 6 5 l 2
1 7 6 l 2
1 8 7 l 2
1 9 8 l 2
1 _ * r Y
Y * * * X
X * _ r X
X _ _ * halt
2 * * l 2
2 _ _ l 3
3 * 1 r 4
3 1 0 l 3
4 * * r 4
4 _ _ r A

Compte à rebours à partir de l'entrée en base 10 tout en comptant à partir de 0 en base 2. En décrémentant zéro, il efface le bloc d'entrée et se termine.

SuperJedi224
la source
2

Javascript 59

o='';i=parseInt(prompt());do{o=(i&1)+o}while(i>>=1)alert(o)
Michael M.
la source
Vous pouvez utiliser à la +xplace deparseInt(x)
Cyoce
2

Perl, 44

C'est mon tout premier programme Perl, alors pardonnez-moi si cela peut être facilement approfondi. Edit: Merci @primo d'avoir retiré 7 caractères de ma réponse.

$x=<>;do{@s=($x&1,@s)}while($x>>=1);print@s

$x=<>;do{push@s,$x&1}while($x>>=1);print reverse@s

La logique est essentiellement la même que ma précédente solution C.

Utilise également 64 bits.

user12205
la source
1
Vous pouvez enregistrer les reverseen construisant les arrière du tableau: @s=($x&1,@s).
primo
1
Maintenant que le concours est terminé, le meilleur que j'ai trouvé 34: $\=$_%2 .$\while$_=$_>>1||<>;print. Ou, si les options de ligne de commande comptent un octet chacune, 27: 1while$\=$_%2 .$\,$_>>=1}{using -p.
primo
2

Javascript - 56 48 et 36 28 caractères

  • Ne fonctionne pas avec des nombres négatifs.

Merci à @Blender d'avoir rasé 8 caractères.

Ce formulaire prend en entrée et affiche la sortie, 48 caractères:

x=prompt();for(a="";x;x=~~(x/2))a=x%2+a;alert(a)

Si juste une instruction qui met dans une variable ala forme binaire d'une variable xest nécessaire (et vous ne vous embêtez pas à détruire la xvaleur comme effet secondaire), la voici avec 28 caractères:

for(a="";x;x=~~(x/2))a=x%2+a
Victor Stafusa
la source
1
Vous pouvez remplacer Math.floorpar ~~, car la plage des nombres est petite.
Blender
@Blender Merci, je savais qu'il existait un moyen, je ne pouvais tout simplement pas le trouver.
Victor Stafusa
@Victor Je ne connais pas le javascript donc je peux me tromper mais à la fin quand vous dites que a=x%2+acela pourrait être raccourci a+=x%2? Cela fonctionne dans toutes les langues que je connais.
Albert Renshaw
@AlbertRenshaw Non, ce serait la même chose que a=a+x%2, mais c'est +pour la concaténation de chaînes. C'est-à-dire que votre suggestion entraîne les chiffres dans l'ordre inverse.
Victor Stafusa
@Victor Ah! Merci!
Albert Renshaw
2

Python - 61 60 caractères

x=input();print"".join("01"[x>>i&1]for i in range(15,-1,-1))
C0deH4cker
la source
2
Vous pouvez vous débarrasser de l'espace entre printet "".
Blender
@Blender J'étais sur le point de suggérer la même chose :)
Albert Renshaw
@Blender Ha vrai, je n'ai même pas remarqué. Terminé!
C0deH4cker
si vous l'appelez depuis la ligne de commande, vous pouvez laisser de côté printcar il renvoie automatiquement le résultat
paul.oderso
2

C, 55 caractères

Imprime un zéro de tête supplémentaire (pour 2 octets).
La récursivité à l'intérieur printfinverse l'ordre d'impression, donc l'algorithme extrait les bits de droite à gauche mais imprime de gauche à droite.

EDIT : a enregistré un caractère en utilisant putcharau lieu de printf.

f(x){(x*=x<0?-printf("-"):1)&&f(x/2);putchar(48+x%2);}
ugoren
la source
2

Dyalog APL , 11 octets

2|⌊⎕÷2*⌽⍳16

2|La division reste lorsqu'elle est divisée par deux de
la valeur arrondie de
l'entrée
÷divisée par chacun de
2*deux à la puissance de chacun de
⍳16{0, 1, 2, ..., 15}

Requiert ⎕IO←0ce qui est par défaut sur de nombreux systèmes.

TryAPL en ligne!

Adam
la source
1

C, 81

char b[17];i=15;main(x){scanf("%d",&x);while(i+1)b[i--]=(x&1)+48,x>>=1;puts(b);}

La sortie a strictement 16 bits (y compris les zéros de remplissage)

user12205
la source
1

Script d'applications + Google Sheets, 147 144 121 octets

Scénario

function j(decNumb){var str='';do{str=String(decNumb%2)+str;decNumb=decNumb/2|0;}while(decNumb>=1);return parseInt(str);}

Feuille

=j(b1)

Version modifiée de ce script par ZygD.

weatherman115
la source
Pouvez-vous supprimer des espaces?
NoOneIsHere
1

Haskell, 66 octets

c 0=0
c n=c(div n 2)*10+mod n 2
b('-':r)='-':b r
b r=show.c.read$r

Appelez avec b "-1023", ajouter main=interact bun programme complet ou essayer sur Ideon.

ceffectue la conversion des entiers positifs.
b r=show.c.read$rconvertit une chaîne en nombre, applique cet reconvertit en chaîne.
b('-':r)='-':b rsupprime un début possible -et le ré-ajoute au résultat.

Laikoni
la source
1

PowerShell, 59 87 82 70 octets

+28 octets pour prendre en charge les nombres négatifs.
-12 octets grâce à @ ASCII uniquement

param($d)$m=$d-lt0;while($d){$n="01"[$d%2]+$n;$d=($d-$d%2)/2}'-'*$m+$n

Essayez-le en ligne!

Adapté de ce code . Prend l'entrée via un paramètre de ligne de commande -d.

Gabriel Mills
la source
Et les numéros avec signe?
mazzy
73?
ASCII uniquement
oh wait 70
ASCII uniquement
1

APL (NARS), 17 caractères, 34 octets

{2∣⌊⍵÷2*(⍺-1)..0}

Il s'agit d'une copie et d'une modification de la réponse d'Adam /codegolf//a/90107 de la façon dont on peut ajouter le paramètre pour la longueur des bits, et ⎕IO pour cette fonction (voici ⎕IO = 1) devrait n'ont aucune importance ...

  f←{2∣⌊⍵÷2*(⍺-1)..0}
  16 f 2
0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 
  32 f 2
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 
  32 f ¯1
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 
  16 f ¯1
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 
  64 f ¯12345678
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 0 1 0 0 0 0 1 1 1 0 0 1 1 1 1 0 1 0 1 1 0 0 1 0 

il semble facile de gérer le nombre de bits de cette façon (j'ai vérifié que le dernier résultat devrait être correct)

RosLuP
la source
0

Smalltalk (Smalltalk / X), 63/78

la première version crée une chaîne intermédiaire (78):

t:=Number readFrom:Stdin.
((15to:1by:-1)collect:[:i|$0+(t>>i&1)]as:String)print

en fait, il n'est pas nécessaire de créer la chaîne; il suffit de sortir les caractères (63):

t:=Number readFrom:Stdin.
15to:1by:-1 do:[:i|($0+(t>>i&1))print]

mhmh - existe-t-il un moyen plus court de lire un nombre?

blabla999
la source
0

Python 3.x: 65 caractères

b=lambda n:n<2 and'01'[n]or b(n//2)+b(n%2);print(b(int(input())))
dan04
la source
0

Bash, 44

f=b+=n/2**e%2*10**e,2**e++/n?f=b:f;echo $[f]

Passez une valeur d'entrée au script via la variable d'environnement n . La représentation décimale du résultat binaire ne peut pas dépasser LONG_MAX.

Cela doit également être compatible avec ksh93et zshsi bet esont initialisés 0et une expansion arithmétique appropriée est utilisée.

ormaaj
la source
1
Je ne crois pas que cela soit valide car il suppose que cela nest déjà défini, ce qui en fait un extrait. Cela pourrait être corrigé en prenant l'entrée comme argument de ligne de commande et en le définissant ndans votre script.
un spaghetto du
@quartata Les variables dans un contexte mathématique en shell sont implicitement nulles. Aux fins du golf, il est plus logique de faire n=127 sh -c '...'que sh -c 'n=$1 ...' _ 127. Il n'y a aucune raison de préférer l'un à l'autre dans ce cas, car ils sont tous deux un moyen parfaitement typique de transmettre des valeurs.
ormaaj
0

C # - 104

string p(int d){var r="";long i=1;while(r.Length<=64){var g=d&i;r=(g!=0)? "1"+r:"0"+r;i=i<<1;}return r;}

Cette méthode convertira les nombres décimaux en binaires jusqu'à 64 bits.

Lorsqu'elle est exécutée, la méthode ci-dessus dans Linqpad - rr = p (-32768); rr.Dump ();

Production: 01111111111111111111111111111111111111111111111111000000000000000

Rajesh
la source
La spécification appelle "une chaîne d'entrée". Il semble que cette méthode accepte un int.
Poke
0

Java 8, 80 71 octets

n->{String r="";for(int i=n<0?-n:n;i>0;i/=2)r=i%2+r;return n==0?"0":r;}

-9 octets en raison d'une règle dans les commentaires. Les entrées négatives en base 10 peuvent renvoyer la valeur positive / absolue en base 2 comme sortie apparemment.

Explication:

Essayez-le en ligne.

n->{                   // Method with integer parameter and String return-type
  String r="";         //  Result-String, starting empty
  for(int i=n<0?-n:n;  //  Start `i` at the absolute (non-negative) value of the input
      i>0;             //  Loop as long as `i` is not 0
      i/=2)            //    After every iteration: integer-divide `i` by 2
    r=i%2+r;           //   Prepend the result with `i` modulo-2
  return n==0?         //  If the input is 0:
          "0"          //   Return literal "0"
         :             //  Else:
          r;           //   Return the result-String
Kevin Cruijssen
la source
0

Kotlin , 82 octets

{s:String->{var i=s.toInt()
var r=""
(0..15).map{r="${i and 1}$r"
i=i shr 1}
r}()}

Essayez-le en ligne!

JohnWells
la source
0

Petit de base , 133 octets

Un script qui entre et sort de la TextWindowconsole.

n=TextWindow.Read()
While n>0
c=c+1
x[c]=Math.Remainder(n,2)
n=Math.Floor(n/2)
EndWhile
For i=0To c-1
TextWindow.Write(x[c-i])
EndFor

Essayez-le sur SmallBasic.com Nécessite Silverlight et doit donc être exécuté dans IE.

Les E / S sont prises / données depuis la console noire.

-22 octets grâce à @Neil

Taylor Scott
la source
Tu ne peux pas utiliser For i=0To c-1?
Neil
@Neil - Je peux absolument. Superbe capture!
Taylor Scott
0

MATL , 15 17 octets

t0<?16Ww+]`2&\t]x

Essayez-le sur MATL en ligne

TIO

(+2 octets supprimant le premier 0 pour les nombres négatifs, le bit de signe doit être le premier bit.)

La sortie sur MATL Online doit être lue de bas en haut (MSB est en bas).

La partie principale est assez simple: `2&\t= alors que la valeur est supérieure à 0, divisez par 2 et accumulez les restes.

Gérer les nombres négatifs et leur donner la représentation du complément à 2 était la partie délicate. En fin de compte, je suis allé avec le " soustraire de2N"méthode pour obtenir le complément d'un deux. Comme nous ne sommes tenus de gérer que les valeurs jusqu'à -32768, pour les nombres négatifs, le code crée 216=65536avec 16W, ajoute l'entrée à cela (par exemple 65536 + (-42)), ce qui donne quelque chose que MATLAB voit comme un nombre positif mais représente la représentation binaire signée de l'entrée sous forme de 16 bits.

Sundar - Rétablir Monica
la source