Java 为什么是Integer.MAX_值+;1==Integer.MIN\u值?

Java 为什么是Integer.MAX_值+;1==Integer.MIN\u值?,java,integer,integer-overflow,twos-complement,jls,Java,Integer,Integer Overflow,Twos Complement,Jls,System.out.println(Integer.MAX\u值+1==Integer.MIN\u值) 这是真的 我知道Java中的整数是32位的,不能超过231-1,但我不明白为什么在其MAX\u值中添加1会导致MIN\u值,而不会出现某种异常。没有提到像Ruby那样将透明转换为更大的类型 这种行为是在什么地方指定的吗?我能相信它吗?当你越过国际日期线时,日期会改变的原因也是一样的:那里有一个不连续性。它内置于二进制加法的本质中。因为整数溢出。当它溢出时,下一个值是Integer.MIN\u

System.out.println(Integer.MAX\u值+1==Integer.MIN\u值)

这是真的

我知道Java中的整数是32位的,不能超过231-1,但我不明白为什么在其
MAX\u值
中添加1会导致
MIN\u值
,而不会出现某种异常。没有提到像Ruby那样将透明转换为更大的类型


这种行为是在什么地方指定的吗?我能相信它吗?

当你越过国际日期线时,日期会改变的原因也是一样的:那里有一个不连续性。它内置于二进制加法的本质中。

因为整数溢出。当它溢出时,下一个值是
Integer.MIN\u value

如果整数加法溢出,则结果是数学和的低阶位,如某些足够大的2的补码格式所示。如果发生溢出,则结果的符号与两个操作数值的数学和的符号不同


您必须了解整数值是如何以二进制形式表示的,以及二进制加法是如何工作的。Java使用一种称为2的补码的表示法,其中数字的第一位表示其符号。每当将1添加到最大的java整数(其位号为0)时,其位号变为1,数字变为负数

此链接详细介绍了:

--

Java语言规范在此处处理此行为:

如果整数加法溢出,则结果是数学和的低阶位,如某些足够大的2的补码格式所示。如果发生溢出,则结果的符号与两个操作数值的数学和的符号不同


这意味着您可以依赖此行为。

当您将
3
(二进制
11
)添加到1(二进制
1
)时,您必须从右侧开始更改为
0
(二进制
0
)所有二进制
1
,直到得到0为止,您应该将其更改为
1
<代码>整数。最大值
的所有位置都用
1
填充,因此只剩下
0
s

整数存储溢出,并且:

内置整数运算符不会以任何方式指示溢出或下溢。如果需要对空引用进行取消装箱转换,整数运算符可以抛出
NullPointerException
。除此之外,唯一可以引发异常的整数运算符是整数除法运算符
/
和整数余数运算符
%
,它们在右操作数为零时引发
算术异常
,以及递增和递减运算符
++
(,)和
-
(,),如果需要装箱转换,并且没有足够的内存来执行转换,则会抛出一个
OutOfMemoryError

4位存储器中的示例:

MAX_INT: 0111 (7)
MIN_INT: 1000 (-8)
最大积分+1:

 0111+
 0001
 ----
 1000

这是一个众所周知的问题,与整数在二进制层表示为向下有关。当你把2的补码的最大值加上1,你就得到了最小值。老实说,在java出现之前,所有整数的行为都是这样的,在java语言中改变这种行为会增加整数数学的开销,并使来自其他语言的程序员感到困惑。

在大多数处理器上,算术指令在溢出时没有故障模式。他们设置了一个必须检查的标志。这是一个额外的指令,所以可能会慢一些。为了使语言实现尽可能快,经常指定语言忽略错误并继续。对于Java,行为在中指定。对于C语言,该语言没有指定行为,但现代处理器的行为将类似于Java

我相信有人建议(笨拙的)JavaSE8库抛出溢出和未签名操作。我相信在DSP世界中流行的一种行为是将值钳制在最大值,因此
Integer.MAX\u VALUE+1==Integer.MAX\u VALUE
[不是Java]


我相信未来的语言会使用任意精度的整数,但暂时不会。需要更昂贵的编译器设计才能快速运行。

导致溢出和两个兼容的自然计数进入“第二个循环”,我们在最右边的位置2147483647,求和1后,我们出现在最左边的位置-2147483648,下一个递增是-2147483647,-2147483646,-2147483645。。。如此类推到最右边,一次又一次,它的本质是求和机对这个位的深度

一些例子:

int a = 2147483647;

System.out.println(a);
电话:2147483647

System.out.println(a+1);
给出:-2147483648(导致溢出和两个符合性的自然计数进入“第二个循环”,我们在最右边的位置2147483647,在求和1之后,我们出现在最左边的位置2147483648,下一个递增的位置是2147483648,-2147483647,-2147483646,…因此,再往最右边一次,再往上一次,它在这个位深度上的求和机器的性质)

给出:-2147483645(-2147483647+2似乎符合数学逻辑)

给出:2147483647(-2147483647-1->-2147483648,-2147483648-1->2147483647前面的答案中描述的一些循环)

给出:-2(2147483647+2147483647->-2147483648+2147483646数学逻辑)


给出:-4(2147483647+2147483647+2147483647+2147483647->-2147483648+2147483646+2147483647+2147483647->-2-2(根据上一个答案)->-4)`

易于理解的字节示例=>

这里我们强制加法并将其转换为字节。 因此,当我们达到127(一个字节的最大可能值)并加上1时,值从127翻转过来(如图所示),变成-128。 该值开始围绕类型旋转

同样是
System.out.println(2-a); 
System.out.println(-2-a);
System.out.println(2*a);
System.out.println(4*a);
byte a=127;//max value for byte
byte b=1;

byte c=(byte) (a+b);//assigns -128
System.out.println(c);//prints -128
int int1=Integer.MAX_VALUE+1;
System.out.println(int1); //prints -2147483648
System.out.println(Integer.MIN_VALUE); //prints -2147483648

//below prints 128 as converted to int as not forced with casting
System.out.println(Byte.MAX_VALUE+1);