java - 当已经溢出时是否可以预测算术结果?

标签 java

假设我们有 int n = 2 ^ 31 然后 n-1 = 0111111111111111111111111111111,这是我在本地可以得到的。

我的猜测:首先将n转换为long -> 减法 -> 切片以适合int

System.out.println(n);
System.out.println(Integer.toBinaryString(n-1) + " : " + Integer.bitCount(n-1));
System.out.println(n-1);


// output 

-2147483648
1111111111111111111111111111111 : 31
2147483647

但是我没有找到规范来验证我的猜测,有吗?

来自Integer overflow wiki .

When an arithmetic operation produces a result larger than the maximum above for an N-bit integer, an overflow reduces the result to modulo N-th power of 2, retaining only the least significant bits of the result and effectively causing a wrap around.

如果我的猜测完全错误,那么它实际上是如何运作的?有什么链接可以引用吗?

任何帮助将不胜感激:)

最佳答案

这就是二进制补码算术的工作原理。

根据 JLS §15.18.2,从 2^31 中减去 1 与 2^31 加 -1 相同。 ,

For both integer and floating-point subtraction, it is always the case that a-b produces the same result as a+(-b).

还有那个

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.

现在我们可以用二进制计算 2^31 和 -1 的和。 2^31 是一个 1 后跟 31 个零,其二进制补码为 -2147483648。 -1 的补码是 32,所以我们有:

 1000 0000 0000 0000 0000 0000 0000 0000
+1111 1111 1111 1111 1111 1111 1111 1111

正如您所看到的,左侧的最后一位溢出了,但根据第二个摘录,我们忽略了这一点。将所有这些加起来,我们得到:

0111 1111 1111 1111 1111 1111 1111 1111

这是 2147483647

关于java - 当已经溢出时是否可以预测算术结果?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56161565/

相关文章:

java - hsqldb : Database lock acquisition when connecting to a file db

java - 如何使用哈希表查找重复和唯一的字符串条目

java - 如何在文本编辑器中设计撤销和重做?

java - 函数返回空(范围问题)

java - 循环中的 getLayoutInflater().inflate() 总是返回第一个 View

java - Java播放的24位音频不正确

java - PDF 的编码问题

java - 求一串由运算符分隔的数字的总和

java - 适用于 Windows 的安装程序

java - 查询多态 Hibernate 属性