Converti dalla base 10 alla base 2 senza conversioni base incorporate


16

Contesto :

Ti è stato assegnato un compito per convertire i numeri di base 10 in base 2 senza utilizzare alcuna funzione di conversione di base premade. Non è possibile utilizzare alcuna libreria importata.

Problema :

Converti una stringa di input dalla base 10 (decimale) alla base 2 (binaria). Non è possibile utilizzare codici / funzioni / metodi di conversione di base predefiniti o librerie importate. Poiché si tratta di , vincerà la risposta più breve in byte.

L'input sarà compreso tra -32768 e 32767 (includi la gestione dei byte di segno nel tuo codice)


3
D: cosa significa "sign byte handling" - devo generare "-xxxx" per un numero negativo? Quindi alcuni di noi hanno torto, incl. io, come ho prodotto "11 ... 11" per -1 (aka come unsigned)
blabla999

Gestione del byte di segno: l'MSB delle variabili firmate controlla se sono negative
TheDoctor

1
certo, ma devo> stamparli <come segno '-' seguito da magnitudo?
blabla999,

@ blabla999 - No, non lo fai
TheDoctor,

3
the MSB of signed variables controls if they are negative- sembra un po 'di segno, tuttavia, come -32768..32767suggerisce l'intervallo , vuoi il complemento di 2. Allora, quale vuoi? ..
mniip,

Risposte:


4

GolfScript - 17 byte

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

Non molto più dettagliato di quello incorporato ~2base.


1
Non conosco golfscript, ma alcune sequenze di esempio mi portano a concludere che è necessario rimuovere il~
user12205

@ace Poiché l'input iniziale è una stringa "37", ad esempio, l'operazione "37" & 1(in infix) è un'operazione saggia. Il ~davanti converte l'input in un numero intero.
primo

Ho fatto il mio test qui golfscript.apphb.com/… significa che questo interprete non è corretto? (Mi dispiace, non so davvero nulla di golfscript)
user12205,

2
L'interprete è corretto; poiché hai inserito il valore intero 10nello stack, non è necessario valutarlo. Tuttavia, quando letto da stdin, l'input sarà una stringa ( test qui ). La descrizione del problema indica inoltre esplicitamente che l'input è una stringa.
primo

12

JavaScript, 46

for(x=prompt(o='');x;x>>>=1)o=(x&1)+o;alert(o)

Lol, non sapevo nemmeno che >>>=esistesse un operatore a 4 caratteri ( )! +1 (Inoltre, se lo esegui nella console, puoi salvare gli ultimi 9 caratteri.)
Maniglia della porta

1
Non è composto da 4 caratteri, sono due operatori: >>> è lo spostamento a destra bit a bit 0, seguito da un compito. Prova: x=8; x>>>=1; x;e x=8; x>>>1; x;- nel primo caso, il valore di x è cambiato; nel secondo no.
Graham Charles,

3
@GrahamCharles >>>=è un singolo operatore .
primo

Bene, guarda quello! Grazie, @primo ... impari qualcosa ogni giorno!
Graham Charles,

2
@ComFreek Questo rovescerebbe l'ordine delle cifre
copia il

4

Brainf * ck, 98 77

Ovviamente questo non ha lo scopo di vincere, ma quale sarebbe una competizione se non avesse una soluzione Brainfk

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

Dal momento che brainfk può gestire solo numeri interi a 8 bit e nessun aspetto negativo, suppongo che non rispetti completamente le regole, ma hey non ci sono mai stato per vincerlo.

Questo effettivamente funziona per l'input a 16 bit se il tuo interprete supporta

Ho anche ottenuto l'output in valori ASCII

Ecco il codice annotato:

++[>++++<-]                       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

Algoritmo più breve (77):

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

Questo può gestire solo numeri interi a 8 bit.

L'algoritmo funziona utilizzando un contatore binario che in realtà è molto breve (un incremento è >[->]++[-<+]-<-che quindi stabilisce i bit. Il problema è che è difficile stampare tutti i bit

Quest'ultimo algoritmo può essere adattato per adattarsi a qualsiasi numero di bit a spese dei byte. Per poter gestire numeri interi a N bit, per la codifica sono necessari 53 + 3 * N byte.

esempi:

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

3

Risposta APL obbligatoria - 21 22

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

Esempi:

      "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

È possibile ridurre con quasi il 50% usando ⎕IO←0, e restituendo un array di bit invece di una stringa: 2|⌊⎕÷2*⊖⍳16.
Adám,

3

Codice di Turing Machine, 272 byte

Come al solito, sto usando la sintassi della tabella delle regole definita qui. Puoi provarlo su quel sito o, in alternativa, usando questa implementazione java.

Gran parte del codice viene copiato dal mio convertitore decimale-esadecimale qui.

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

Conta alla rovescia dall'ingresso in base 10 mentre conta da 0 in base 2. Al decremento di zero, cancella il blocco di input e termina.


2

Javascript 59

o='';i=parseInt(prompt());do{o=(i&1)+o}while(i>>=1)alert(o)

Puoi usare +xinvece diparseInt(x)
Cyoce il

2

Perl, 44

Questo è il mio primo programma Perl di sempre, quindi per favore perdonami se questo può essere facilmente risolto. Modifica: Grazie @primo per aver rimosso 7 caratteri dalla mia risposta.

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

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

La logica è essenzialmente la stessa della mia precedente soluzione C.

Inoltre, utilizza 64 bit.


1
È possibile salvare il reversecostruendo le all'indietro matrice: @s=($x&1,@s).
primo

1
Ora che la gara è finita, il migliore che ho trovato è stato 34: $\=$_%2 .$\while$_=$_>>1||<>;print. Oppure, se le opzioni della riga di comando contano un byte ciascuna, 27: 1while$\=$_%2 .$\,$_>>=1}{using -p.
primo

2

Javascript - 56 48 e 36 28 caratteri

  • Non funziona con numeri negativi.

Grazie a @Blender per la rasatura di 8 caratteri.

Questo modulo accetta input e mostra output, 48 caratteri:

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

Se è necessaria solo un'istruzione che inserisce in una variabile ala forma binaria di una variabile x(e non ti preoccupi di distruggere il xvalore come effetto collaterale), eccolo con 28 caratteri:

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

1
È possibile sostituire Math.floorcon ~~, poiché l'intervallo per i numeri è piccolo.
Blender,

@Blender Grazie, sapevo che esisteva in qualche modo, non riuscivo a trovarlo.
Victor Stafusa,

@Victor Non conosco javascript, quindi potrei sbagliarmi, ma alla fine quando dici che a=x%2+apotrebbe essere abbreviato a+=x%2? Funziona in tutte le lingue che conosco.
Albert Renshaw,

@AlbertRenshaw No, sarebbe lo stesso di a=a+x%2, ma +è per la concatenazione di stringhe. Vale a dire, il tuo suggerimento comporta le cifre nell'ordine inverso.
Victor Stafusa,

@Victor Ah! Grazie!
Albert Renshaw,

2

Python - 61 60 caratteri

x=input();print"".join("01"[x>>i&1]for i in range(15,-1,-1))

2
Puoi liberarti dello spazio tra printe "".
Blender,

@Blender Stavo per suggerire la stessa cosa :)
Albert Renshaw,

@Blender Ha vero, non me ne sono nemmeno accorto. Fatto!
C0deH4cker,

se lo chiami dalla riga di comando potresti lasciarlo da parte printpoiché restituisce automaticamente il risultato
paul.oderso

2

C, 55 caratteri

Stampa uno zero iniziale aggiuntivo (per motivi di 2 byte).
Ricorsione all'internoprintf inverte l'ordine di stampa, quindi l'algoritmo estrae i bit da destra a sinistra ma stampa da sinistra a destra.

EDIT : salvato un carattere usando putcharinvece di printf.

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

2

Dyalog APL , 11 byte

2|⌊⎕÷2*⌽⍳16

2|Il resto della divisione dimezzato del
valore arrotondato per difetto
dell'input
÷diviso per ciascuno dei
2*due alla potenza di ciascuno di
⍳16{0, 1, 2, ..., 15}

Richiede il ⎕IO←0valore predefinito su molti sistemi.

ProvaAPL online!


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);}

L'output ha rigorosamente 16 bit (inclusi zeri di riempimento)


1

Apps Script + Fogli Google, 147 144 121 byte

copione

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

Foglio

=j(b1)

Versione modificata di questo script di ZygD.


Puoi rimuovere degli spazi?
NoOneIsHere il

1

Haskell, 66 byte

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

Chiama con b "-1023", aggiungi main=interact bper un programma completo o provalo su Ideon.

cesegue la conversione per numeri interi positivi.
b r=show.c.read$rconverte una stringa in un numero, si applica ce la converte nuovamente in stringa.
b('-':r)='-':b rtoglie un possibile vantaggio -e lo ricollega al risultato.



1

APL (NARS), 17 caratteri, 34 byte

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

È una copia e modifica della risposta di Adam /codegolf//a/90107 nel modo in cui è possibile aggiungere il parametro per la lunghezza dei bit e ⎕IO per questa funzione (qui è ⎕IO = 1) dovrebbe non ha importanza ...

  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 

sembra facile gestire il numero di bit in questo modo (ho pensato che l'ultimo risultato dovesse essere giusto)


0

Smalltalk (Smalltalk / X), 63/78

la prima versione crea una stringa intermedia (78):

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

in realtà, non è necessario creare la stringa; ho appena emesso i caratteri (63):

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

mhmh - c'è un modo più breve per leggere un numero?


0

Python 3.x: 65 caratteri

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

0

Bash, 44

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

Passa un valore di input allo script attraverso la variabile di ambiente n. La rappresentazione decimale del risultato binario non può superare LONG_MAX.

Questo dovrebbe anche essere compatibile con ksh93e zshse be esono inizializzati 0e viene utilizzata la corretta espansione aritmetica.


1
Non credo che ciò sia valido poiché presume che nsia già definito, rendendolo uno snippet. Ciò potrebbe essere risolto prendendo l'input come argomento della riga di comando e impostandolo nsu quello nel tuo script.
uno spaghetto il

@quartata Le variabili in un contesto matematico nella shell sono implicitamente zero. Ai fini del golf ha più senso n=127 sh -c '...'che sh -c 'n=$1 ...' _ 127. Non c'è motivo di preferire l'uno all'altro in questo caso in quanto sono entrambi un modo perfettamente tipico per passare valori.
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;}

Questo metodo converte i decimali in binari fino a 64bit.

When executed the above method in Linqpad - rr = p(-32768); rr.Dump();

Output: 01111111111111111111111111111111111111111111111111000000000000000


La specifica richiede "una stringa di input". Sembra che questo metodo accetta un int.
Colpisci il

0

Java 8, 80 71 byte

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

-9 byte a causa di una regola nei commenti. Gli input negativi di base 10 potrebbero restituire il valore positivo / assoluto di base 2 come output apparentemente.

Spiegazione:

Provalo online.

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


0

Piccolo di base , 133 byte

Uno script che immette e restituisce alla 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

Provalo su SmallBasic.com Richiede Silverlight e quindi deve essere eseguito in IE.

Gli I / O vengono acquisiti / dati dalla console nera.

-22 byte grazie a @Neil


Non puoi usare For i=0To c-1?
Neil,

@Neil - Posso assolutamente. Ottima cattura!
Taylor Scott,

0

MATL , 15 17 byte

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

Provalo su MATL online

TIO

(+2 byte rimuovendo lo 0 iniziale per i numeri negativi, il bit di segno dovrebbe essere il primo bit.)

L'output su MATL Online deve essere letto dal basso verso l'alto (MSB è in fondo).

The main part is pretty simple: `2&\t = while the value is greater than 0, divide by 2 and accumulate the remainders.

Handling negative numbers and giving them 2's complement representation was the tricky part. In the end I went with the "subtract from 2N" method of getting a number's two's complement. Since we're only required to handle values upto -32768, for negative numbers the code creates 216=65536 with 16W, adds the input to that (eg. 65536 + (-42)), which gives something MATLAB sees as a positive number but represents the input's signed binary representation in 16-bit form.




Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.