这是我将使用的代码...
public class foo {
public static void main(String [] args){
int a = (int) Math.pow(2, 30);
double d = (a + a - 1.0);
double f = (a + a - 1);
System.out.println(d);
System.out.println(f);
}
}
输出为 -2.147483649E9和 2.147483647E9。
我不明白为什么要打印出这些值。我的理解是 a + a 将超过 int 的限制,因此将转换为负数,但是,f 是正数。我希望两者都是负数,但 f 将是小数,而 d 由于整数除法而是一个点为 0 的双精度。
在第一种情况下,a + a
溢出到Integer.MIN_VALUE
,然后你切换到一个double
上下文,-1.0
给出一个负数(Integer.MIN_VALUE - 1
),因为一个double
可以容纳一个小于Integer.MIN_VALUE
的数字。
在第二个示例中,您停留在int
上下文中,这意味着a + a
溢出到Integer.MIN_VALUE
,然后从该下溢中减去 1 并带您回到Integer.MAX_VALUE
。
一步一步地拆开它,就会发现答案。
首先,我们观察到a + a == Integer.MIN_VALUE
Ideone.com
演示。
接下来,如果计算表达式a + a - 1.0
,则从左到右计算,即相当于(a + a) - 1.0
,相当于Integer.MIN_VALUE - 1.0
。由于右手边是double
,Integer.MIN_VALUE
也转换为double
,结果为负数。
最后,如果计算表达式a + a - 1
,则等效于Integer.MIN_VALUE - 1
。整个操作在int
空间中用环算术完成,从MIN_VALUE
的子1
计算到MAX_VALUE
。