C/C++操作符的优先级和结合性问题浅析

举报
李锐博恩 发表于 2021/07/15 23:50:06 2021/07/15
【摘要】 两个相邻操作符的执行顺序由它们的优先级决定。例如: a + b*c,在这个表达式中,乘法和加法操作符是两个相邻的操作符,由于乘法的优先级比加法高,所以乘法运算先于加法运算执行。编译器在这里别无选择,它必须先执行乘法运算。 如果它们的优先级相同,它们的执行顺序由它们的结合性决定。例如:a + b + c,由于 + 操作符的结合性是由左到右(L-R),所以先计算a+b,然后计算...

两个相邻操作符的执行顺序由它们的优先级决定。例如: a + b*c,在这个表达式中,乘法和加法操作符是两个相邻的操作符,由于乘法的优先级比加法高,所以乘法运算先于加法运算执行。编译器在这里别无选择,它必须先执行乘法运算。

如果它们的优先级相同,它们的执行顺序由它们的结合性决定。例如:a + b + c,由于 + 操作符的结合性是由左到右(L-R),所以先计算a+b,然后计算(a+b)+c。

除此之外,编译器可以自由决定使用任何顺序对表达式进行求值,只要它不违背逗号、&&、||和?:操作符所施加的限制。

上面这句话是什么意思呢?举个例子说明: a*b+ c*d + e*f,对于这个表达式,如果仅有优先级决定这个表达式的求值顺序,那么所有3个乘法运算将在所有加法运算之前进行。事实上,这个顺序并不是必需的。实际上,只要保证每个乘法运算在它相邻的加法运算之前执行即可。

例如这个表达式可能会以下面的顺序进行:

a*b

c*d

(a*b)+(c*d)

e*f

(a*b)+(c*d)+(e*f)

注意第一个加法运算在最后一个乘法运算之前执行。

如果这个表达式按下面这个顺序执行,其结果也是一样的:

c*d

e*f

a*b

(a*b)+(c*d)

(a*b)+(c*d)+(e*f)

如果编译器足够变态,当然可以以这个顺序进行,因为标准并没有对此进行限制。


注:除此之外,我还需要讲解一下上文提到的,只要只要它不违背逗号、&&、||和?:操作符所施加的限制。

这说明上面提到的这个几个操作符的特殊性,它们对求值顺序进行了控制。

首先是逗操作符:

用法如下:

expression1,expression2,...,expressionN

逗号表达式将两个或多个表达式分隔开来。这些表达式自左向右逐个求值,整个逗号表达式的值就是最后那个表达式的值。

说完了它的用法,那么整个逗号操作符的意义何在

请看下面的代码示例:

其次,就是&&与||这两个操作符,它们是逻辑操作符,逻辑操作符具有短路性质,就是如果表达式的值根据左操作数就可以确定,那么它就不在对右操作数进行求值。

例如,a > 5 && a < 10

首先我们知道,比较操作符的优先级高于逻辑操作符,故上面的表达式等价于:

( a > 5 ) && ( a < 10)

但是,尽管&&操作符的优先级低,但是它仍然会对两个关系表达式施加限制,下面是它的工作原理:

&&操作符的左操作数总是首先进行求值,如果它的值为真,那么就紧接着对右操作数求值。如果左操作数为假,那么右操作数不再求值,因为整个表达式肯定是假的,右操作数已经无关紧要。

同理,可以类似地分析||。

最后一个就是?:条件操作符。例如 a>b?c=a:c=b;

它的优先级低于比较操作符,赋值操作符,但是它仍然对它们进行控制。

作用原理是,如果a>b成立的话,执行语句c=a;否则c=b。


下表截取C和指针给出的优先级、结合性等比较全的版本:


如果感觉上面的比较乱,那再来一个中文版本:

参考:C/C++里面的运算符的优先级和结合性

这里写图片描述


口诀:

参考:C/C++运算符优先级和口诀

括号成员第一;        //括号运算符[]() 成员运算符.  ->

全体单目第二;        //所有的单目运算符比如++、 --、 +(正)、 -(负) 、指针运算*、&乘除余三,加减四;   //这个"余"是指取余运算即%

移位五,关系六;    //移位运算符:<< >> ,关系:> < >= <= 等

等于(与)不等排第七;    //即== 和!=

位与异或和位或;    //这几个都是位运算: 位与(&)异或(^)位或(|)    

"三分天下"八九十;  

逻辑或跟与;            //逻辑运算符:|| 和 &&

十二和十一;            //注意顺序:优先级(||)  底于 优先级(&&) 

条件高于赋值,        //三目运算符优先级排到13 位只比赋值运算符和","高

逗号运算级最低!    //逗号运算符优先级最低 

 

文章来源: reborn.blog.csdn.net,作者:李锐博恩,版权归原作者所有,如需转载,请联系作者。

原文链接:reborn.blog.csdn.net/article/details/82149622

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。