I'm messing around with bitwise operators, and I was trying to convert a negative byte to an unsigned 8 bit value, and this is what people suggested:
System.out.println(-20 & 0xFF); //bitwise AND on negative number and 255
So, this works perfectly, and returns 236, but why? As far as I'm concerned:
00010100 //binary representation of -20
11111111 //binary representation of 0xFF or 255
--------
00010100 //it returns the same exact thing, so it's either -20 or 20
Why does it work? I think I've missed something pretty simple, but I can't seem to grasp it.
Also, if I do it with a positive number below 256, it returns the same number. I can't seem to understand what Java does with these numbers.
The literals in Java are in the form of int. So when you say -20 & 0xFF, this is what happens:
11111111 11111111 11111111 11101100 //-20 -ve nos are stored in 2's compliment form
& 00000000 00000000 00000000 11111111 // 0xFF
-------- -------- -------- --------
00000000 00000000 00000000 11101100 // 236
Since the negetaive values are stored in 2's compliment form, you get the value 236.
When you perfrom 20 & 0xFF, this happens:
00000000 00000000 00000000 00010100 // 20 -ve nos are stored in 2's compliment form
& 00000000 00000000 00000000 11111111 // 0xFF
-------- -------- -------- --------
00000000 00000000 00000000 00010100 // 20
A byte is a signed value held in 8 bits and may be in the range -128 to 127.
The left most bit is used as the sign bit.
System.out.println(-20 & 0xFF); has nothing to do with bytes, this is an int operation.
The binary representation of -20, as a byte is: 1110_1100
1110_1100 & 1111_1111 = 1110_1100
If you want unsigned, there's char to play with, but you're not going to be happy. Realistically, Java doesn't have unsigned.
Negatives are stored in '2s Complement' form, eg:
1111_1111 == -1
But why?
Under 2s complement to make a negative number, all the bits are flipped (1s complement) and 1 is added (making 2s complement - two operations)
So
0000_0000 - Zero
-0000_0001 - minus one
---------
1111_1110 - Ones complement - (this would be xor 1111_1111)
+0000_0001 - plus one - we're converting to 2s complement, not doing math
---------
1111_1111 - -1 in 2s complement
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