为什么C中的逻辑运算符在不必要时不求值整个表达式? [英] Why do logical operators in C not evaluate the entire expression when it's not necessary to?

查看:43
本文介绍了为什么C中的逻辑运算符在不必要时不求值整个表达式?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在读我的计算机体系结构课程的教科书,偶然发现了这一说法.

I was reading my textbook for my computer architecture class and I came across this statement.

逻辑运算符'&&'和'||'与它们的位级副本'&'和'|'之间的第二个重要区别是,逻辑运算符不评估第二个参数是否可以通过评估第一个参数确定表达式的结果.因此,例如,表达式a && 5/a绝不会导致被零除,而表达式p && *p++绝不会导致对空指针的解引用. (《计算机系统:程序员的观点》,科比和奥哈拉隆,第3版,第57页)

A second important distinction between the logical operators '&&' and '||' versus their bit-level counterparts '&' and '|' is that the logical operators do not evaluate their second argument if the result of the expression can be determined by evaluating the first argument. Thus, for example, the expression a && 5/a will never cause a division by zero, and the expression p && *p++ will never cause the dereferencing of a null pointer. (Computer Systems: A Programmer's Perspective by Bryant and O'Hallaron, 3rd Edition, p. 57)

我的问题是,为什么C中的逻辑运算符会那样表现?使用作者的a && 5/a示例,C是否不需要评估整个表达式,因为&&要求两个谓词都为真?不失一般性,我的问题同样适用于他的第二个例子.

My question is why do logical operators in C behave like that? Using the author's example of a && 5/a, wouldn't C need to evaluate the whole expression because && requires both predicates to be true? Without loss of generality, my same question applies to his second example.

推荐答案

短路是一种性能增强,碰巧可用于其他目的.

Short-circuiting is a performance enhancement that happens to be useful for other purposes.

您说"C不需要评估整个表达式,因为&&要求两个谓词都为真吗?"但是考虑一下.如果&&的左侧为假,那么右侧的计算结果是否重要? false && truefalse && false,结果相同:false.

You say "wouldn't C need to evaluate the whole expression because && requires both predicates to be true?" But think about it. If the left hand side of the && is false, does it matter what the right hand side evaluates to? false && true or false && false, the result is the same: false.

因此,当确定&&的左侧为假,或确定||的左侧为真时,右侧的值无关紧要,可以跳过.通过消除评估潜在的昂贵第二测试的需求,这可以使代码更快.试想一下,如果右侧调用了一个函数,该函数扫描了整个文件以查找给定的字符串?如果第一个测试意味着您已经知道组合答案,您是否不想跳过该测试?

So when the left hand side of an && is determined to be false, or the left hand side of a || is determined to be true, the value on the right doesn't matter, and can be skipped. This makes the code faster by removing the need to evaluate a potentially expensive second test. Imagine if the right-hand side called a function that scanned a whole file for a given string? Wouldn't you want that test skipped if the first test meant you already knew the combined answer?

C决定从保证短路到保证评估顺序,因为这意味着像您提供的安全测试一样可行.只要测试是幂等的,或者仅在未短路时才打算产生副作用,则此功能是可取的.

C decided to go beyond guaranteeing short-circuiting to guaranteeing order of evaluation because it means safety tests like the one you provide are possible. As long as the tests are idempotent, or the side-effects are intended to occur only when not short-circuited, this feature is desirable.

这篇关于为什么C中的逻辑运算符在不必要时不求值整个表达式?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆