1

I have a 20-bytes byte[].
I need to read the first 4 bytes and convert them in a single unsigned integer and then in a string.
The bytes generate a large integer so when i convert to a integer and then in a string, I have a negative number.
Example: 0x53, 0x2D, 0x78, 0xAA. I convert them with:

        hash = bHash[0]|bHash[1]<<8|bHash[2]<<16|bHash[3]<<24;
        keyid = String.valueOf(hash);
        keyid = Integer.toString(hash);

and I have in both cases: "-1434964653" but i need to generate "2860002643".

SteMMo
  • 392
  • 1
  • 4
  • 23

2 Answers2

1

Since there is no unsigned int in Java, use long type:

 long hash = (bHash[0]|bHash[1]<<8|bHash[2]<<16|bHash[3]<<24)&0xFFFFFFFFl;
 String keyid = String.valueOf(hash);
 keyid = Long.toString(hash);
Alexei Kaigorodov
  • 13,189
  • 1
  • 21
  • 38
0

I wrote up a little example.

This is the library that I use to manipulate bytes.

@Test
public void readUnsignedInt () {
    //0x53, 0x2D, 0x78, 0xAA.
    //http://stackoverflow.com/questions/19874527/conversion-from-bytes-to-large-unsigned-integer-and-string
    ByteBuf buf = ByteBuf.create ( 20 );
    buf.addByte ( 0xAA );
    buf.addByte ( 0x78 );
    buf.addByte ( 0x2D );
    buf.addByte ( 0x53 );

    byte[] bytes = buf.readForRecycle ();

ByteBuf is a lightweight reusable buffer. Boon is a library for implementing slice notation in Java and other utilities.

You can read unsigned bytes with idxUnsignedInt, the second arg is the offset.

    long val = idxUnsignedInt ( bytes, 0 );

    boolean ok = true;

BTW die throws a runtime exception and returns a boolean so you can short circuit or it to expressions to create a type of assert that can't be turned off by the compiler. :)

    ok |= val ==  2860002643L || die(); //die if not equal to 2860002643L

You can also read longs (you did not ask but I wanted to show you anyway).

    buf.add ( 2860002643L );

    bytes = buf.readForRecycle ();

    val = idxLong ( bytes, 0 );

    ok |= val ==  2860002643L || die();

You can also add unsigned ints to a byte array buffer. Good for testing.

    //add unsigned int to the byte buffer.
    buf.addUnsignedInt ( 2860002643L );

    //read the byte array of the buffer
    bytes = buf.readForRecycle ();

    //Read the unsigned int from the array, 2nd arg is offset
    val = idxUnsignedInt ( bytes, 0 );

    //Convert it to string and print it to console
    puts("" + val);

    ok |= val ==  2860002643L || die();

The above covers all parts of your question. It reads it and converts it to a string.

Here is is converted to a string again.

    ok |= ("" + val).equals("2860002643") || die();

Now for just a few more combinations.

    //Read the unsigned int from the array, 2nd arg is offset
    byte [] bytes2 = new byte[] {
            (byte)0xAA, 0x78, 0x2D, 0x53,   0,
                  0,       0,    0,    0,   0,
                  0,       0,    0,    0,   0,
                  0 ,      0,    0,    0,   0 };


    val = idxUnsignedInt ( bytes2, 0 );

    ok |= val ==  2860002643L || die();


    //Deal direct with bytes
    byte [] bytes3 = new byte[20];


    unsignedIntTo ( bytes3, 0,  2860002643L);

    val = idxUnsignedInt ( bytes2, 0 );

    ok |= val ==  2860002643L || die();

}

I can never remember exactly how to do this, and I got sick of looking it up so I wrote this stuff.

You can read more about ByteBuf here. :)

https://github.com/RichardHightower/boon/wiki/Auto-Growable-Byte-Buffer-like-a-ByteBuilder

RickHigh
  • 1,808
  • 20
  • 16