What happens when you increment an integer beyond its max value?
In Java, what happens when you increment an int (or byte/short/long) beyond it's max value? Does it wrap around to the max negative value?
Does AtomicInteger.getAndIncrement()
also behave in the same manner?
From the Java Language Specification section on integer operations:
The built-in integer operators do not indicate overflow or underflow in any way.
The results are specified by the language and independent of the JVM version: Integer.MAX_VALUE + 1 == Integer.MIN_VALUE
and Integer.MIN_VALUE - 1 == Integer.MAX_VALUE
. The same goes for the other integer types.
The atomic integer objects (AtomicInteger
, AtomicLong
, etc.) use the normal integer operators internally, so getAndDecrement()
, etc. behave this way as well.
If you do something like this:
int x = 2147483647;
x++;
If you now print out x
, it will have the value -2147483648
.
As jterrace says, the Java run-time will "wrap' the result to the Integer.MIN_VALUE of -2147483648.
But that is Mathematically incorrect! The correct Mathematically answer is 2147483648. But an 'int' can't have a value of 2147483648. The 'int' boundaries are -2147483648 to 2147483647
So why doesn't Java throw an exception? Good question! An Array object would.
But language authors know the scope of their primitive types, so they use the 'wrapping' technique to avoid a costly exception.
You, as a developer, must test for these type boundaries. A simple test for incrementing would be
if(x++ == Integer.MIN_VALUE)
//boundary exceeded
A simple test for decrementing would be
if(x-- == Integer.MAX_VALUE)
//boundary exceeded
A complete test for both would be
if(x++ == Integer.MIN_VALUE || x-- == Integer.MAX_VALUE)
//boundary exceeded
What happens is an extra bit is added to the furthest right bit and the order decrements as a negatively signed int ... Notice what happens after 'int_32';
int _0 = 0b0000000000000000000000000000000;
int _1 = 0b0000000000000000000000000000001;
int _2 = 0b0000000000000000000000000000010;
int _3 = 0b0000000000000000000000000000100;
int _4 = 0b0000000000000000000000000001000;
int _5 = 0b0000000000000000000000000010000;
int _6 = 0b0000000000000000000000000100000;
int _7 = 0b0000000000000000000000001000000;
int _8 = 0b0000000000000000000000010000000;
int _9 = 0b0000000000000000000000100000000;
int _10 = 0b0000000000000000000001000000000;
int _11 = 0b0000000000000000000010000000000;
int _12 = 0b0000000000000000000100000000000;
int _13 = 0b0000000000000000001000000000000;
int _14 = 0b0000000000000000010000000000000;
int _15 = 0b0000000000000000100000000000000;
int _16 = 0b0000000000000001000000000000000;
int _17 = 0b0000000000000010000000000000000;
int _18 = 0b0000000000000100000000000000000;
int _19 = 0b0000000000001000000000000000000;
int _20 = 0b0000000000010000000000000000000;
int _21 = 0b0000000000100000000000000000000;
int _22 = 0b0000000001000000000000000000000;
int _23 = 0b0000000010000000000000000000000;
int _24 = 0b0000000100000000000000000000000;
int _25 = 0b0000001000000000000000000000000;
int _26 = 0b0000010000000000000000000000000;
int _27 = 0b0000100000000000000000000000000;
int _28 = 0b0001000000000000000000000000000;
int _29 = 0b0010000000000000000000000000000;
int _30 = 0b0100000000000000000000000000000;
int _31 = 0b1000000000000000000000000000000;
int _32 = 0b1111111111111111111111111111111;
int _XX = 0b10000000000000000000000000000000; // numeric overflow.
int _33 = 0b10000000000000000000000000000001;
int _34 = 0b11000000000000000000000000000000;
int _35 = 0b11100000000000000000000000000000;
int _36 = 0b11110000000000000000000000000000;
int _37 = 0b11111000000000000000000000000000;
int _38 = 0b11111100000000000000000000000000;
int _39 = 0b11111110000000000000000000000000;
int _40 = 0b11111111000000000000000000000000;
int _41 = 0b11111111100000000000000000000000;
int _42 = 0b11111111110000000000000000000000;
int _43 = 0b11111111111000000000000000000000;
int _44 = 0b11111111111100000000000000000000;
int _45 = 0b11111111111110000000000000000000;
int _46 = 0b11111111111111000000000000000000;
int _47 = 0b11111111111111100000000000000000;
int _48 = 0b11111111111111110000000000000000;
int _49 = 0b11111111111111111000000000000000;
int _50 = 0b11111111111111111100000000000000;
int _51 = 0b11111111111111111110000000000000;
int _52 = 0b11111111111111111111000000000000;
int _53 = 0b11111111111111111111100000000000;
int _54 = 0b11111111111111111111110000000000;
int _55 = 0b11111111111111111111111000000000;
int _56 = 0b11111111111111111111111100000000;
int _57 = 0b11111111111111111111111110000000;
int _58 = 0b11111111111111111111111111000000;
int _59 = 0b11111111111111111111111111100000;
int _60 = 0b11111111111111111111111111110000;
int _61 = 0b11111111111111111111111111111000;
int _62 = 0b11111111111111111111111111111100;
int _63 = 0b11111111111111111111111111111110;
int _64 = 0b11111111111111111111111111111111;
System.out.println( " _0 = " + _0 );
System.out.println( " _1 = " + _1 );
System.out.println( " _2 = " + _2 );
System.out.println( " _3 = " + _3 );
System.out.println( " _4 = " + _4 );
System.out.println( " _5 = " + _5 );
System.out.println( " _6 = " + _6 );
System.out.println( " _7 = " + _7 );
System.out.println( " _8 = " + _8 );
System.out.println( " _9 = " + _9 );
System.out.println( " _10 = " + _10 );
System.out.println( " _11 = " + _11 );
System.out.println( " _12 = " + _12 );
System.out.println( " _13 = " + _13 );
System.out.println( " _14 = " + _14 );
System.out.println( " _15 = " + _15 );
System.out.println( " _16 = " + _16 );
System.out.println( " _17 = " + _17 );
System.out.println( " _18 = " + _18 );
System.out.println( " _19 = " + _19 );
System.out.println( " _20 = " + _20 );
System.out.println( " _21 = " + _21 );
System.out.println( " _22 = " + _22 );
System.out.println( " _23 = " + _23 );
System.out.println( " _24 = " + _24 );
System.out.println( " _25 = " + _25 );
System.out.println( " _26 = " + _26 );
System.out.println( " _27 = " + _27 );
System.out.println( " _28 = " + _28 );
System.out.println( " _29 = " + _29 );
System.out.println( " _30 = " + _30 );
System.out.println( " _31 = " + _31 );
System.out.println( " _32 = " + _32 );
System.out.println( " _xx = " + _xx ); // -2147483648
System.out.println( " _33 = " + _33 );
System.out.println( " _34 = " + _34 );
System.out.println( " _35 = " + _35 );
System.out.println( " _36 = " + _36 );
System.out.println( " _37 = " + _37 );
System.out.println( " _38 = " + _38 );
System.out.println( " _39 = " + _39 );
System.out.println( " _40 = " + _40 );
System.out.println( " _41 = " + _41 );
System.out.println( " _42 = " + _42 );
System.out.println( " _43 = " + _43 );
System.out.println( " _44 = " + _44 );
System.out.println( " _45 = " + _45 );
System.out.println( " _46 = " + _46 );
System.out.println( " _47 = " + _47 );
System.out.println( " _48 = " + _48 );
System.out.println( " _49 = " + _49 );
System.out.println( " _50 = " + _50 );
System.out.println( " _51 = " + _51 );
System.out.println( " _52 = " + _52 );
System.out.println( " _53 = " + _53 );
System.out.println( " _54 = " + _54 );
System.out.println( " _55 = " + _55 );
System.out.println( " _56 = " + _56 );
System.out.println( " _57 = " + _57 );
System.out.println( " _58 = " + _58 );
System.out.println( " _59 = " + _59 );
System.out.println( " _60 = " + _60 );
System.out.println( " _61 = " + _61 );
System.out.println( " _62 = " + _62 );
System.out.println( " _63 = " + _63 );
System.out.println( " _64 = " + _64 );
If an integer addition overflows, then the result is the low-order bits of the mathematical sum as represented in some sufficiently large two's-complement format. If overflow occurs, then the sign of the result is not the same as the sign of the mathematical sum of the two operand values.
http://java.sun.com/docs/books/jls/second_edition/html/expressions.doc.html#13510