Reputation: 31
Consider the following code.
why such asymmetry ?
Upvotes: 0
Views: 361
Reputation: 213213
From JLS §15.19:
If the promoted type of the left-hand operand is int, only the five lowest-order bits of the right-hand operand are used as the shift distance. It is as if the right-hand operand were subjected to a bitwise logical AND operator & (§15.22.1) with the mask value 0x1f (0b11111). The shift distance actually used is therefore always in the range 0 to 31, inclusive.
So, it's not that <<
is circular and >>
is not. It's just the value you chose, that made you believe that.
With shifting 1
by 34
, considering the lowest 5 bits:
1 >> 34 === 1 >> 2 === 0
1 << 34 === 1 << 2 === 4
Since 34 & 0x1F == 2
.
Now, take some larger value, for which bit shifting by 2
will not get you 0
technically:
4 >> 34 == 4 >> 2 == 1
4 << 34 == 4 << 34 == 16
The shift distance for int
type are always calculated taking the 5 lowest-order bits. It's not a circular shift operation. Neither of them are. This is how they are intended to behave.
Upvotes: 5
Reputation: 533472
Shift only uses the lower 5 bits for an int and the lower 6 bit for a long.
1 >> 34 = 0
This is the same as 1 >> 2 which is 0 as this is not circular rotation.
1 << 34 = 4 // circular shift
This is the same as 1 << 2 as the shift only uses the lower 5 bits for an int and the lower 6 bit for a long.
This is not circular shifting.
e.g.
Integer.MIN_VALUE << 1 // is 0
Upvotes: 2
Reputation: 5102
When shifting right with the signed shift operator 1>>34
, following the oracle documentation, the left is filled up with the sign, in this case, as 1 is positive, the sign is 0. The one gets lost with the first shift 1>>1 = 0
When shifting left with the signed shift operator 1<<34
the following happens:
0x0001<<34 = (0x0001 << 32) << 2 = 0x0004 = 4
Upvotes: 0