2014-05-07 18 views
5

Lo scenario semplice: Hai un array di bytePerché il metodo java Integer.toBinaryString (-128) emette sette cifre?

byte[] message = { 1, 2, 3 };

Per stamparlo in formato binario è possibile utilizzare il codice:

for (byte b : message) { 
    System.out.println(Integer.toBinaryString(0x100 + b).substring(1)); 
} 

(Got che il codice da this stack overflow thread)

E ottieni questo risultato:

00000001 
00000010 
00000011 



Ma se si etichetta un -128 sulla fine ...

byte[] message = { 1, 2, 3, -128 };

00000001 
00000010 
00000011 
0000000 

WOAH! Un numero binario a sette cifre? Sento che questo è qualcosa a che fare con il complemento a due, ma più cerco di leggerlo, più mi confondo. Mi aspettavo 10000000 ad apparire nella quarta riga, invece ...

Qualcuno può spiegare perché Integer.toBinaryString di -128 è sette cifre in termini relativamente semplici?


Ye olde javadoc dice The unsigned integer value is the argument plus 2^32 if the argument is negative; otherwise it is equal to the argument. This value is converted to a string of ASCII digits in binary (base 2) with no extra leading 0s. ma come ho detto ... mi confonde.



Il contesto di tutta questa faccenda è che sto provando codifica alcune delle funzioni SHA in Java. Non chiedermi perché, non so nemmeno ... Sono solo curioso/sfidandomi/frustrando me stesso :)

Il padding di un messaggio per l'uso nella funzione SHA-256 (rendendolo un multiplo di 512 in lunghezza bit) secondo the documentation è la concatenazione di:

  1. il messaggio originale
  2. Un singolo 1 bit
  3. 0 bit fino agli ultimi 64 bit
  4. la lunghezza messaggio originale un valore a 64 bit

Dato che i miei messaggi saranno molto probabilmente in ASCII codici a 8 bit, ho semplicemente bisogno di contrassegnare una 10000000 a 2 # ... quindi posso solo contare il numero di byte da aggiungere 0, ho shouldn Non è necessario pianificare messaggi che non siano multipli di 8. Il problema è rendere questo 10000000.

risposta

6
(-128 + 0x100) = 
(256 - 128) = 128 = 
0b10000000 

Integer.toBinaryString(0b10000000) = "10000000" 

"10000000".substring(1) = "0000000" 
+0

Questo è il motivo per cui non dovrei essere autorizzato a programmare la notte. Ci scusiamo per il tempo sprecato ahaha – snickers10m

1

C'è un bug nel thread di overflow dello stack da cui è stato copiato. 0x100 è 256 in decimale, quindi ...

0x100 + 1 = 257 = 0b100000001 (9 digits) 
0x100 + (-128) = 128 = 0b10000000 (8 digits) 

In altre parole, dal momento che è inferiore a 128 Byte.MAX_VALUE, non si ottiene l'effetto di riempimento che il manifesto destinato. Puoi scegliere un valore più grande da battere - prova 0x200 e spoglia i primi due caratteri ??

FWIW, è comprensibile che questi tipi di errori b/c valori di byte negativi sono un po 'una strana cosa java. Oh bene.

+0

Quindi, nel contesto di ciò che stavo cercando di realizzare ... Il byte nell'array equivale a 10000000, anche se il modo in cui l'ho visualizzato non lo ha fatto? C'è un altro modo in cui dovrei inserire un 1 come richiesto dalla funzione SHA? – snickers10m

+0

In realtà non visualizzerò il file binario ... Stavo solo facendo questo per verificare se stava funzionando ... Devo solo avere un array di byte con il messaggio seguito da un 10000000 che funzionerà in operazioni bit a bit. – snickers10m

Problemi correlati