Java 中的 i = i++ 问题

Java 中的 i = i++ 问题

int i = 0;
i = i++;
System.out.println(i);  // 0

问最后的输出结果是什么。我这两天才开始看 Java,第一眼就认为肯定是输出 1 ,但如果结果真的这么直观就不会出成笔试题了。实际运行一下,结果居然是输出 0。

如果把 i = i++ 换成 i = ++i 或者干脆换成 i++。输出结果就是 1 了。为了完整性,把替换后的代码也贴一下。

int i = 0;
i++;
System.out.println(i);  // 1
int i = 0;
i = ++i;
System.out.println(i);  // 1

解释

这个问题其实想明白了就很简单,只需要理解两个关键的地方:1. 表达式的返回值。 2. 临时变量。不信我们先来分析大家都知道的 i++++i 的区别。假设有下面一段 Java 代码:

// e.g.1
int i = 0;
int j = 0;
int a = ++i;  // a=1, i=1
int b = j++;  // b=0, j=1

问最后 i j a b 的值各是什么。相信很多人都能得到正确答案。所以我把答案直接注释在代码中了。很多人也能解释个所以然来。但我们还是来分析一下:

a 的结果是表达式 ++i 的值,而 b 的结果是表达式 j++ 的值。大多数人都知道 ++i 返回的是 i 自增以后的值,而 j++ 返回的是 j 自增以前的值。a b 值不一样,也就是表达式 ++i 和表达式 j++ 的返回值不一样。

上面说这么啰嗦就是为了让大家注意到表达式的返回值的概念。表达式都是有返回值的,不然就不能放在赋值操作符右边了。而且无论多么复杂的表达式都是在表达式计算完后才返回一个值(注意是计算完后)。表达式 ++i 的返回值就是 i 自增后的值,而表达式 j++ 的返回值是 j 自增前的值。

OK,我们终于引入了表达式的返回值这个概念。再思考一下, 表达式 ++i 直接在 i 自增完后返回 i 的值就行。那 j++ 要返回 j 自增前的值,怎么做到?难道先返回 j 的值,然后再让 j 自增吗?不行,因为表达式计算结束后才能返回一个值。编译器普遍的做法是创建一个临时变量来保存 j 自增前的值,在 j 自增完后再返回这个临时变量的值。所以 b = j++ 底层发生的步骤如下:

step1: temp = j; // 创建一个临时变量 temp 保存 j 的值,这个 temp 也是整个表达式的返回值
step2: 对 j 进行自增操作
step3: 将表达式的返回值 temp 赋值给 b
  • 1
  • 2
  • 3

然后临时变量 temp 的使命就完成了。

注:可能有部分人误以为:表达式 j++ 是先返回 j 的值,然后再对 j 进行自增操作。这种理解是错误的。如果表达式都返回了,还计算个球。表达式只有在计算完后才会进行返回。无论多么复杂的表达式,返回值都在最后一步。

OK,到了这里,原始问题就很清晰了。

int i = 0;
i = i++;
System.out.println(i);  // 0
  • 1
  • 2
  • 3

i = i++ 对应的步骤如下:

step1: 创建一个临时变量 temp 保存 i 的值 // temp=i=0,temp 也是整个表达式的返回值
step2: 对 i 进行自增操作  // i 的值变成了 1
step3: 返回表达式的值,也就是将 temp 赋值 给 i  // i 的值变成了 temp 的值,所以 i 又变成了 0

--------------------- 作者:流沙的刺客 来源:CSDN 原文:https://blog.csdn.net/candcplusplus/article/details/54558333?utm_source=copy 版权声明:本文为博主原创文章,转载请附上博文链接!

猜你喜欢

转载自blog.csdn.net/xuyao625010693/article/details/83003916