&&
的左侧部分是否始终在右侧部分之前进行评估?
我想知道,因为我想知道我是否可以改变
if(i > 0)
if(someFunc(arr[i-1], arr[i]))
//do work
到
if(i > 0 && someFunc(arr[i-1], arr[i]))
如果首先评估右侧并引用arr[0-1]
,这会导致未定义的行为吗?
答案 0 :(得分:3)
是的,由于逻辑&&
运算符的short-circuit行为,如果&&
第二个表达式仅在first为true时进行求值。阅读以下内容:
6.5.13逻辑AND运算符
4与按位二进制
&
运算符不同,&&
运算符保证left-to-right
评估; 在评估第一个操作数后有一个序列点。如果是第一个操作数 比较等于0,第二个操作数不评估。
来自Is short-circuiting boolean operators mandated in C/C++? And evaluation order?
因此,如果i > 0
为false(例如,如果i = 0
),那么i > 0
表达式的结果将为false,然后将不会调用第二个操作数someFunc(arr[i-1], arr[i]
(已评估)。
因此,if(i > 0 && someFunc(arr[i-1], arr[i]))
代码是安全的,但要小心i - 1
不应该是>最大索引值arr[]
。真的,我会更喜欢这种形式,如果比较嵌套的if块(扁平比嵌套更好)。
来自@ Maroun Maroun的回答"Is there any reason for asking if(1 || Foo())
?"可能对您有所帮助的其他信息:
if(a && b)
- 如果a
为false
,则b
不会被检查。if(a && b)
- 如果a
为true
,则会检查b
,因为如果它是false
,则表达式为{{} 1}}。false
- 如果if(a || b)
为a
,则true
不会被检查,因为无论如何这都是b
。true
- 如果if(a || b)
为a
,则会检查false
,因为如果b
为b
,那么它就会被true
是true
。
答案 1 :(得分:1)
是。从左到右保证运营商&&
,||
,,
和? :
(三元运营商)的评估顺序。在这些操作数的左右子表达式之间出现sequence point。这些运算符(&&
,||
和,
)的左子表达式的所有副作用都在访问其右子表达式之前完成。
如果首先评估右侧并引用arr[0-1]
,是否会导致未定义的行为?
是。如果是这种情况,则会导致未定义的行为。 (但它不会发生这种情况,因此不存在任何未定义的行为。)