2011-08-23 11 views
8

Mam specyfikację, która odczytuje kolejne dwa bajty są podpisane int.jak odczytać podpisane int z bajtów w java?

Aby dowiedzieć się, że w Javie Mam następujący

Kiedy czytam podpisanego int w Java przy użyciu następującego kodu otrzymuję wartość 65449

logiki obliczania unsigned

int a =(byte[1] & 0xff) <<8 

int b =(byte[0] & 0xff) <<0 

int c = a+b 

Wierzę, że to jest złe, ponieważ jeśli ja i z 0xff otrzymam niepodpisany odpowiednik

, więc usunąłem 0xff 0xi logika, jak podano poniżej

int a = byte[1] <<8 
int b = byte[0] << 0 
int c = a+b 
which gives me the value -343 
byte[1] =-1 
byte[0]=-87 

ja próbuje zrównoważyć te wartości z okazji spec brzmi ale to wygląda wrong.Since wielkość sterty robi wchodzą w to.

Która z metod jest odpowiednia do obliczania int w java?

Oto jak spec idzie

somespec() { xtype 8 uint8 xStyle 16 int16 } xStyle: liczba całkowita ze znakiem, który reprezentuje przesunięcie (w bajtach) od początku tego Widget() strukturę początku struktury xStyle(), która wyraża odziedziczonej style zdefiniowane przez widget strony, a także style, które mają zastosowanie do tego widgetu.

+0

Czy możesz pokazać przykład wejścia i pożądany wynik? nie jest jasne .. – MByD

+0

Przeczytałem to ze strumienia przy użyciu specyfikacji. Odczytuję dwa bajty zgodnie ze specyfikacją i wartościami, gdy czytam w tablicy bajtów po przekonwertowaniu na poszczególne bajty są: bajt [1] = - 1 i bajt [0] = - 87 mówią w tablicy bajtów zawierającej dwa bajty. Specyfikacja oznacza te dwa bajty jako podpisane int i nie wiem, co jest poprawnym wyjściem. – Siva

Odpowiedz

13

Jeśli wartość jest 16-bitową chcesz short i int jest 32-bitowy, który może również posiadać te same wartości, ale nie tak naturalnie.

Wygląda na to, że chcesz mieć podpisaną małą 16-bitową wartość endian.

byte[] bytes = 
short s = ByteBuffer.wrap(bytes).order(ByteOrder.LITTLE_ENDIAN).getShort(); 

lub

short s = (short) ((bytes[0] & 0xff) | (bytes[1] << 8)); 

BTW: Można użyć int ale nie jest tak prosta.

// to get a sign extension. 
int i = ((bytes[0] & 0xff) | (bytes[1] << 8)) <<16>> 16; 

lub

int i = (bytes[0] & 0xff) | (short) (bytes[1] << 8)); 
+0

to działało. dzięki – Siva

2

Nie mogę go skompilować w tej chwili, ale zrobiłbym (zakładając, że byte1 i byte0 są ponownie typu bajtowego).

int result = byte1; 
result = result << 8; 
result = result | byte0; //(binary OR) 
if (result & 0x8000 == 0x8000) { //sign extension 
    result = result | 0xFFFF0000; 
} 

jeśli byte1 i byte0 są ints, trzeba będzie dokonać `& 0xFF

UPDATE ponieważ Java zmusza wyrazem jeśli się być logiczna

+0

jeśli to zrobię, otrzymam przesunięcie -87, spróbuję tego i zobaczę, czy jestem w stanie odczytać wartość w stercie. Czy mógłbyś mi pomóc sprawdzić, czy powinienem przeczytać ten spec somespec() { xtype 8 uint8 xStyle 16 int16} xStyle: Podpisana liczba całkowita reprezentująca przesunięcie (w bajtach) od początku tej struktury Widget() do początku struktury xStyle(), która wyraża odziedziczone style zdefiniowane przez widget strony, jak również style, które odnoszą się konkretnie do tego widgetu. – Siva

2

Spójrz na DataInputStream.readInt(). Możesz albo stamtąd napisać stal, albo po prostu użyć DataInputStream: owinąć swój strumień wejściowy, a następnie łatwo odczytać dane wpisane.

Dla Państwa wygody jest to kod:

public final int readInt() throws IOException { 
    int ch1 = in.read(); 
    int ch2 = in.read(); 
    int ch3 = in.read(); 
    int ch4 = in.read(); 
    if ((ch1 | ch2 | ch3 | ch4) < 0) 
     throw new EOFException(); 
    return ((ch1 << 24) + (ch2 << 16) + (ch3 << 8) + (ch4 << 0)); 
} 
+1

To odczytuje big-endianowe wartości 32-bitowe, uważam, że OP chce mieć małą wartość 16-bitowego endianu. –

4

Zakładając, że bajty [1] jest MSB i bajty [0] jest LSB, i że chcesz odpowiedź być 16-bitowa liczba całkowita:

short res16 = ((bytes[1] << 8) | bytes[0]); 

Następnie, aby uzyskać 32 bitową liczbę całkowitą:

int res32 = res16; // sign extends. 

Nawiasem mówiąc, specyfikacja powinna określać, który z dwóch bajtów jest MSB, a który jest LSB. Jeśli nie, a nie ma żadnych przykładów, nie możesz go wdrożyć!

Gdzieś w specyfikacji powie, jak jest reprezentowane "int16". Wklej tę część. Lub wklej link do specyfikacji, abyśmy mogli sami go przeczytać.

+0

proszę zobaczyć moje zmiany w głównym zapytaniu, podałem, jak spec czyta – Siva

1

Czy masz sposób na znalezienie prawidłowego wyjścia dla danego wejścia? technicznie, rozmiar int wynosi 4 bajty, więc z zaledwie 2 bajtami nie można osiągnąć bitu znaku.

+0

somespec() { xtype 8 uint8 pwStyle 16 int16} Podpisana liczba całkowita reprezentująca przesunięcie (w bajtach) od początku tego widgetu () struktura na początku struktury xStyle(), która wyraża odziedziczone style zdefiniowane przez widget strony jako oraz style, które odnoszą się specjalnie do tego widgetu. – Siva

Powiązane problemy