How to convert negative byte value to either short or integer?

6.7k views Asked by At

We have a file which contains byte array in particular format like header and then followed by data. This file is generated by another java program and then we are reading that same file through another java program in the same format in which it was written.

The program which is making that file, populates lengthOfKey as byte which is right as that's what we need as shown below.

    for (Map.Entry<byte[], byte[]> entry : holder.entrySet()) {
        byte typeKey = 0;

        // getting the key length as byte (that's what we need to do)
        byte lengthOfKey = (byte) entry.getKey().length;
        byte[] actualKey = entry.getKey();
    }

Now as byte can only store maximum value as 127, we are seeing for some of our record lengthOfKey is coming as negative while we read the file as shown below:

Program which is reading the file:

byte keyType = dis.readByte();

// for some record this is coming as negative. For example -74
byte lengthOfKey = dis.readByte();

Now my question is : Is there any way I can find out what was the actual length of key because of that it got converted to -74 while writing it. I mean it should be greater than 127 and that's why it got converted to -74 but what was the actual value?

I think question would be how to convert negative byte value to either short or integer? I just wanted to verify to see what was the actual length of key because of that it got converted to negative value.

3

There are 3 answers

2
rgettman On BEST ANSWER

If the original length from entry.getKey().length is greater than 255, then the actual length information is lost. However, if the original length was between 128 and 255, then it can be retrieved.

The narrowing conversion of casting to byte keeps only the least significant 8 bits, but the 8th bit is now interpreted as -128 instead of 128.

You can perform a bit-and operation with 0xFF, which will retain all bits, but that implicitly widens the value back to an int.

int length = lengthOfKey & 0xFF;

lengthOfKey (byte = -74): 10110110

Widening it to an int, with sign extension:

lengthOfKey (int = -74): 11111111 11111111 11111111 10110110

Masking out the last 8 bits as an int:

length (int = 182): 00000000 00000000 00000000 10110110

That will convert a negative byte back to a number between 128 and 255.

0
Gilbert Le Blanc On

To convert an assumed unsigned byte to an int.

int value = (byteValue >= (byte) 0) ? (int) byteValue : 256 + (int) byteValue; 
0
dimo414 On

If you use Guava, it provides a number of unsigned math utilities, including UnsignedBytes.

UnsignedBytes.toInt(lengthOfKey);

Notice their implementation of toInt() is exactly what @rgettman suggests.