为什么按位运算符的优先级比比较低?


63

有人可以解释其原理,为什么在一堆最流行的语言中(请参见下面的注释),比较运算符(==,!=,<,>,<=,> =)的优先级要高于按位运算符(&,|,^ ,〜)?

我认为我从未遇到过这种优先次序自然的用途。总是这样的:

  if( (x & MASK) == CORRECT ) ...   // Chosen bits are in correct setting, rest unimportant

  if( (x ^ x_prev) == SET )      // only, and exactly SET bit changed

  if( (x & REQUIRED) < REQUIRED )   // Not all conditions satisfied

我要使用的情况:

  flags = ( x == 6 | 2 );     // set bit 0 when x is 6, bit 1 always.

几乎不存在。

语言设计者决定这种运算符优先级的动机是什么?


例如,除SQL外,排名前12种语言中的所有语言都与langpop.com 上的“ 编程语言流行度”列表上的语言相同:C,Java,C ++,PHP,JavaScript,Python,C#,Perl,SQL,Ruby,Shell,Visual Basic。


16
C语言中原始设计的错误
棘轮怪胎

7
@gnat,投诉的重点是什么?OP没有说“全部”,只是说“一堆最受欢迎的语言”。绝大多数人遵循这个顺序。在此表中,排名前12位(SQL)中只有一个没有:langpop.com

3
@ dan1111的目的自然是帮助回答者更好地理解所提出的问题并提供更好的答案。您会看到,这里不是The Guessing Game的地方-或如游览页面所述,“这不是讨论论坛。没有闲聊。”
gnat 2013年

7
@gnat,我同意您对猜谜游戏的关注,但是当几乎每种流行语言都表现出上述行为时,我认为这没有资格。

5
@Dunk:常见的“直觉”方法是[arithmetics] [logic operator] [arithmetics]。大多数程序员不喜欢创造括号乱七八糟的if(((x+getLowX()) < getMinX) || ((x-getHighX())>getMaxX())))-大多数会认为在逻辑算术的优先级和写if( ( x + getLowX() < getMinX ) || ( x - getHighX() > getMaxX() )) 假设的优先级+以上<。现在直观上if( x ^ getMask() != PATTERN ) 应该表现出相同的行为,XOR是算术运算符。它被解释为if( x ^ ( getMask() != PATTERN ) )完全违反直觉的事实。
SF。

Answers:


72

语言是从C语言复制过来的,而对于C语言,Dennis Ritchie 解释说,最初,在B语言(可能是C语言早期)中,只有一种形式&会根据上下文进行按位或逻辑上的形式。后来,每个函数都有其运算符:&按位运算符和&&逻辑运算符。然后他继续

他们迟钝的介绍解释了C优先级规则的不足。在B写

if (a == b & c) ...

检查是否a等于bc非零;在这样的条件表达式中,&优先级低于优先==。在从乙转换为C,一个想要替换&通过&&在这样的陈述; 为了减轻转换的麻烦,我们决定相对于保持&运算符的优先级不变==,而只是将的优先级从&&稍微分开&。今天,似乎它会一直最好移动的相对优先级&==,从而简化常见的C成语:测试对另一值的屏蔽值,必须写

if ((a & mask) == b) ...

需要内括号但很容易忘记的地方。


1
如果c=2Or a==b导致了结果~0而没有,那不会失败1吗?
SF。

看来,a == b返回0或1,请参见cm.bell-labs.com/cm/cs/who/dmr/kbman.html
AProgrammer

检查答案中的参考并阅读前面的内容。
SShaheen

1
@MasonWheeler:尤其是在嵌入式系统中,有时有时需要使用类似函数的宏[在某些情况下,它们可以提供比内联函数更好的数量级性能,并且在某些嵌入式系统中可能是至关重要的]。在此类宏中无法进行变量声明;在宏中使用全局变量可能有效,但看起来确实很麻烦。
2014年

6
@MasonWheeler:你能找到数量为1000的Raspberry Pi或Arduino,价格为0.50美元吗?
2014年

7

按位运算符在概念上和外观上都与逻辑运算符相关,这可能解释了为什么它们在优先级表中彼此靠近。也许甚至有人可能会争辩说,&要高于这个水平==却要&&低于这个水平,那将是令人困惑的==

设置优先级先例(!)后,为保持一致性,其他语言可能最好遵循它。

但是,我倾向于同意您的看法,这并非最佳选择。在实际使用中,位运算符更像是数学运算符,而不是逻辑运算符,如果优先将它们与数学运算符组合在一起会更好。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.