I am aware -that in Java- int is 4 bytes. But I wish to covert an int to n-bytes array, where n can be 1, 2, 3, or 4 bytes. I want to have it as signed byte/bytes, so that if I need to convert them back to int (event if it was 1 byte), I get the same signed int. I am fully aware about the possibility of precision loss when converting from int to 3 or lower bytes.
I managed to convert from int to n-byte, but converting it back for a negative number yield unsigned results.
Edit:
int to bytes (parameter n specify the number of bytes required 1,2,3, or 4 regardless of possible precession loss)
public static byte[] intToBytes(int x, int n) {
byte[] bytes = new byte[n];
for (int i = 0; i < n; i++, x >>>= 8)
bytes[i] = (byte) (x & 0xFF);
return bytes;
}
bytes to int (regardless of how many bytes 1,2,3, or 4)
public static int bytesToInt(byte[] x) {
int value = 0;
for(int i = 0; i < x.length; i++)
value += ((long) x[i] & 0xffL) << (8 * i);
return value;
}
There is probably a problem in the bytes to int converter.
The byteValue() method of Integer class of java. lang package converts the given Integer into a byte after a narrowing primitive conversion and returns it (value of integer object as a byte).
An int value can be converted into bytes by using the method int. to_bytes().
When an integer value is converted into a byte, Java cuts-off the left-most 24 bits. We will be using bitwise AND to mask all of the extraneous sign bits.
BigInteger.toByteArray()
will do this for you ...
Returns a byte array containing the two's-complement representation of this
BigInteger
. The byte array will be in big-endian byte-order: the most significant byte is in the zeroth element. The array will contain the minimum number of bytes required to represent thisBigInteger,
including at least one sign bit, which is(ceil((this.bitLength() + 1)/8))
. (This representation is compatible with the(byte[])
constructor.)
Example code:
final BigInteger bi = BigInteger.valueOf(256);
final byte[] bytes = bi.toByteArray();
System.out.println(Arrays.toString(bytes));
Prints:
[1, 0]
To go from the byte array back to a int, use the BigInteger(byte[])
constructor:
final int i = new BigInteger(bytes).intValue();
System.out.println(i);
which prints the expected:
256
Anyway, this is the code I threw together:
public static void main(String[] args) throws Exception {
final byte[] bi = encode(-1);
System.out.println(Arrays.toString(bi));
System.out.println(decode(bi));
}
private static int decode(byte[] bi) {
return bi[3] & 0xFF | (bi[2] & 0xFF) << 8 |
(bi[1] & 0xFF) << 16 | (bi[0] & 0xFF) << 24;
}
private static byte[] encode(int i) {
return new byte[] { (byte) (i >>> 24), (byte) ((i << 8) >>> 24),
(byte) ((i << 16) >>> 24), (byte) ((i << 24) >>> 24)
};
}
Something like:
int unsignedByte = ((int)bytes[i]) & 0xFF;
int n = 0;
n |= unsignedByte << 24;
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With