Java陷阱(三)

来源:互联网 发布:数据库安全技术有哪些 编辑:程序博客网 时间:2024/05/15 06:40

前言:摘自《Java解惑》。这些问题都很经典,可以细细品味。


问题:无情的增量

代码:

/** *无情的增量 * @authorLiangGzone */public class Increment {  publicstatic void main(String[] args) {  intj = 0;  for(int i = 0; i < 100; i++) {  j= j++;  }  System.out.println(j);  }}
分析:当++操作符被置于一个变量值之后时,其作用就是一个后缀增量操作符,表达式j++的值等于j在执行增量操作之前的初始值。因此,前面提到的赋值语句首先保存j的值,然后将j设置为其值加1,最后将j复位到它的初始值。换句话说,这个赋值操作等价于下面的语句序列:

int temp = j;

j = j + 1;

j = temp;

类似的问题:

public class Demo {  publicstatic void main(String[] args) {  intj = 0;  j= j++;  System.out.println(j);  }}
建议不要在单个的表达式中对相同的变量赋值超过一次。


问题:变幻莫测的i

代码:

/** *变幻莫测的i值 * @authorLiangGzone */public class Shifty {   publicstatic void main(String[] args) {       inti = 0;       while(-1 << i != 0)            i++;       System.out.println(i);   }}

分析:常量-1是所有32位都被置位的int数值(0xffffffff)。左移操作符将0移入到由移位所空出的右边的最低位,因此表达式(-1<< i)将i最右边的位设置为0,并保持其余的32 -i位为1。很明显,这个循环将完成32次迭代,因为-1<< i对任何小于32i来说都不等于0。你可能期望终止条件测试在i等于32时返回false,从而使程序打印32,但是它打印的并不是32。实际上,它不会打印任何东西,而是进入了一个无限循环。问题在于(-1<< 32)等于-1而不是0,因为移位操作符之使用其右操作数的低5位作为移位长度。或者是低6位,如果其左操作数是一个long类数值。

建议:如果可能的话,移位长度应该是常量。


问题:什么样的声明能够让下面的循环变成一个无限循环?

While (i == i + 1) {}

代码:

/** *循环者 * @authorLiangGzone */public class LoopDemo {  publicstatic void main(String[] args) {  doublei = 1.0e40;  while(i== i+1){  System.out.println("loop");  }  }}
分析:浮点数操作返回的是最接近其精确的数学结果的浮点数值。一旦毗邻的浮点数值之间的距离大于2,那么对其中的一个浮点数值加1将不会产生任何效果,因为其结果没有达到两个数值之间的一半。对于float类型,加1不会产生任何效果的最小级数是225,即33,554,432;而对于double类型,最小级数是254,大约是1.8 ×1016

建议:用一个double或一个float数值来表示无穷大是可以的。将一个很小的浮点数加到一个很大的浮点数上时,将不会改变大的浮点数的值。


问题:什么样的声明能够让下面的循环变成一个无限循环?

While (i == i + 1) {}

代码:

/** *循环者2 * @authorLiangGzone */public class LoopDemo2 {  publicstatic void main(String[] args) {  doublei = Double.NaN;  while(i!= i){  System.out.println("loop");  }  }}
分析:任何浮点操作,只要它的一个或多个操作数为NaN,那么其结果为NaN。一旦一个计算产生了NaN,它就被损坏了,没有任何更进一步的计算可以修复这样的损坏。NaN值意图使受损的计算继续执行下去,直到方便处理这种情况的地方为止。

建议:floatdouble类型都有一个特殊的NaN值,用来表示不是数字的数量。对于涉及NaN值的计算,其规则很简单也很明智,但是这些规则的结果可能是违背直觉的。


阅读链接:

Java陷阱(一)

Java陷阱(二)

Java陷阱(三)

Java陷阱(四)

Java陷阱(五)

Java陷阱(六)






原创粉丝点击