public class InTheLoop {
public static final int END = Integer.MAX_VALUE;
public static final int BEGIN = END - 100;
public static void main(String[] args) {
int count = 0;
for(int i= BEGIN ; i <= END ; i++) {
count++;
}
System.out.println(count);
}
}
以上代码会输出什么呢?如果不仔细看,可能认为是100,因为循环了100遍,但是仔细观察可以看出,该循环不是典型的惯例用法,所以你认为输出应该是101。其实都不是,如果不是你手动停止该程序,该程序会一直运行下去。
问题的根源在哪呢?
问题在于for循环的条件(Condition)中,注意到 i <= END,即 i <= Integer.MAX_VALUE,当循环到100遍时,i = Integer.MAX_VALUE,下一个循环i++,i由于是int类型,发生上溢,i = Integer.MIN_VALUE,当然小于END,于是i不断变大到Integer.MAX_VALUE,然后上溢变成Integer.MIN_VALUE,周而复始,一直循环下去。
所以问题出在int类型在该场合下表示范围太小,可以把i的类型从int换成long。
public class InTheLoop {
public static final int END = Integer.MAX_VALUE;
public static final int BEGIN = END - 100;
public static void main(String[] args) {
int count = 0;
for(long i= BEGIN ; i <= END ; i++) {
count++;
}
System.out.println(count);
}
}
这样很快就能得到101的答案。
该类问题给语言设计者的教训是,应该对那些在产生溢出时不会抛出异常的算术运算提供支持。