首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >操作符优先级不明确,请解释为什么这里没有遵循运算符的优先顺序?

操作符优先级不明确,请解释为什么这里没有遵循运算符的优先顺序?
EN

Stack Overflow用户
提问于 2013-08-02 01:56:52
回答 3查看 636关注 0票数 4
代码语言:javascript
复制
x = y = z = 1;
z = ++x||++y&&++z;

运算符的优先顺序如下--

代码语言:javascript
复制
(pre-increment) > && > ||

所以答案应该是--

代码语言:javascript
复制
1.  2||2 && 2
2.  2||1
3.  1

print x,y,z should be 2,2,1

但是,答案是2,1,1。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2013-08-02 02:04:39

使用逻辑运算符&&||的表达式从左到右计算:

C99,第6.5.14-4节与按位|运算符不同,||运算符保证从左到右的计算;在计算第一个操作数之后有一个序列点。如果第一个操作数比较不等于0,则不计算第二个操作数。

由于x++不是零,表达式短路评估的一切都向右||,包括它们的副作用。这就是为什么只有x++被计算,所以x变成了2。剩下的变量留在1中,就像它们应该做的那样。

票数 8
EN

Stack Overflow用户

发布于 2013-08-02 02:07:04

优先级与评估顺序不一样。优先级只是确定什么操作数和操作符应该放在一起。计算的确切顺序是未指定的,但逻辑运算符的除外,逻辑运算符按严格的从左到右的顺序进行计算,以启用短路。

因此,由于&&具有更高的优先级,因此首先将变量分组如下:

代码语言:javascript
复制
(++x) || (++y && ++z)

然后,按照从左到右的顺序,计算++x .假设++x是真的,那么整个表达式都是真的。因此,表达式评估是短路的。(++y && ++z)从未被评估过。因此,y和z永远不会增加。

票数 12
EN

Stack Overflow用户

发布于 2013-08-02 02:02:53

表达式中没有序列点:

代码语言:javascript
复制
z = ++x || ++y && ++z;

z的预增量与分配给z之间的关系。

因此,如果对++z进行了实际评估,这将使您立即进入未定义的行为领域,任何事情都可能发生。不允许在没有中间序列点的情况下修改同一对象两次。附件C(来自C99)列出了所有的序列点,这里的控制点遵循一个完整的表达式(整个计算和赋值)。

6.5 Expressions /2声明:

在前一个序列点和下一个序列点之间,对象最多应该通过表达式的计算修改其存储值一次。此外,应只读取先验值以确定要存储的值。

但是,假定x的初始值为1,在这种情况下,表达式的++z部分不会被计算。这并不会降低表达式本身的危险性,因为在起点为x == -1y != -1的情况下,它将调用UB。

在这种情况下,标准的控制部分是6.5.14 Logical OR operator /4

与按位操作数不同的是,保证从左到右的求值;在计算第一个操作数之后有一个序列点。如果第一个操作数比较等于0,则不计算第二个操作数。

因此,首先计算++x,因为它的计算值不是-零,所以从不计算++y && ++z .x增加到2z被设置为该值的“真实性”,或者1y1中保持不变。

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/18007550

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档