为了账号安全,请及时绑定邮箱和手机立即绑定

请教 java中 a+=b+=a+=b 的详细运算过程

请教 java中 a+=b+=a+=b 的详细运算过程

慕雪6442864 2019-03-14 14:11:26
本人使用java3年,也算是个程序小鸟,但是总喜欢把问题研究的透彻。原题是这么个样子:int a = 2,b = 5;a+=b+=a+=b;问最后a,b分别是多少。我原本以为整个过程是这样的0.原式清晰化的表达一下: a+=(b+=(a+=b));1.先算最里面的括号 a+=b //a = 7;2.再算中间括号 b+=a //b = 12;3.计算最后括号 a+=b //a = 19但是实际结果出乎我的意料,答案是a=14 b=12后来我想了一下,出现这样的原因是因为第一次计算最里面的括号并没有给a赋值。也就是说,[color=red]a,b在整个计算过程中,只进行了最后那一次的赋值运算[/color]。但是这个说法遭来了同事的反驳。因此,我在这里发帖询问,[color=blue]想彻底弄清楚,这么个表达式的整个运算过程。如果能顺便提到编译器如何实现这样操作那就更好不过了,还望知道详情的大神不吝赐教,小弟在此叩拜[/color]如果实在是腾不出时间解答这无聊的问题,给点参考资料也许,哪怕给几个搜索关键字(我都不知道该对这样的问题怎么搜索)
查看完整描述

4 回答

?
红糖糍粑

TA贡献1815条经验 获得超6个赞

a+=b+=a+=b; 
等价于
a=a+(b=b+(a=a+b));

1、运算过程中注意a是原子类型 值是拷贝的
2、a=a+(××××); //+结合率是从左到右。 即先将a压栈 然后计算括号内的,这样算就明白了,具体请看用javap -verbose 来观看字节码操作
0: iconst_2

1: istore_1 --->a
2: iconst_5
3: istore_2 --->b
4: iload_1 载入a(2)
5: iload_2 载入b(5)
6: iload_1 载入a(2)
7: iload_2 载入b(5)
8: iadd 7 (第6和7行累计 结果压栈)
9: dup 复制栈顶
10: istore_1 a(7) 把栈顶结果保存到a
11: iadd 12 (栈顶7+第5行)
12: dup 复制12
13: istore_2 b(12) 结果保存到b
14: iadd 12+2(栈顶+第4行)
15: istore_1 a(14)


查看完整回答
反对 回复 2019-04-26
?
慕桂英3389331

TA贡献2036条经验 获得超8个赞

举个例子:int a = 2,b = 5; 
int s = a+b; /赋值运算符是从右到左,也就是 s=7;
有了这个道理那么看这个就很简单了
a+=b+=a+=b;
那么简单分3段;从右到左运算
第一段:a+=b;也就是a=a+b;也就是a=7;
第二段:b+=(a+=b);已知第一段 a+=b=7;
也就是b=b+7;也就是b=5+7=12;
第三段:a+=(b+=(a+=b));已知第二段算 b=12;
那么a+=12;也就是a=a+12;也就是a=14;

查看完整回答
反对 回复 2019-04-26
?
慕运维8079593

TA贡献1876条经验 获得超5个赞

+= 这种运算,是从右到左的计算吗?


查看完整回答
反对 回复 2019-04-26
?
繁花如伊

TA贡献2012条经验 获得超12个赞

a+=b+=a+=b;

此表达式有三个赋值过程, 对a赋值两次, 对b赋值一次

首先是把所有的操作数都压入栈内, 
先计算 最后一个a = a + b ; 计算完赋值a 
然后计算 b= a + (a + b) ; 计算完赋值b, 这里需要注意的是,整个操作的值已经初始化过, 这里 a + (a + b) 前面一个a 的值不是7,应该还是2。
最后计算 a = a + (a + (a + b)) ; 计算完赋值a;


查看完整回答
反对 回复 2019-04-26
  • 4 回答
  • 0 关注
  • 784 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信