Python 是否会懒惰地评估 if 的条件?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/13960657/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-18 10:01:36  来源:igfitidea点击:

Does Python evaluate if's conditions lazily?

pythonlazy-evaluation

提问by ogama8

For example, if I have the following statement:

例如,如果我有以下语句:

if( foo1 or foo2)
    ...
    ...

if foo1 is true, will python check the condition of foo2?

如果 foo1 为真,python 会检查 foo2 的条件吗?

采纳答案by unutbu

Yes, Python evaluates boolean conditions lazily.

是的,Python 懒惰地评估布尔条件。

The docs say,

文件说

The expression x and y first evaluates x; if x is false, its value is returned; otherwise, y is evaluated and the resulting value is returned.

The expression x or y first evaluates x; if x is true, its value is returned; otherwise, y is evaluated and the resulting value is returned.

表达式 x 和 y 首先计算 x;如果 x 为假,则返回其值;否则,计算 y 并返回结果值。

表达式 x 或 y 首先计算 x;如果 x 为真,则返回其值;否则,计算 y 并返回结果值。

回答by jdotjdot

Yes, Python evaluates lazily, so foo2will not be checked.

是的,Pythonfoo2会惰性求值,因此不会被检查。

I use this all the time for grabbing items from dictionary-like objects if I don't know if the key exists:

如果我不知道密钥是否存在,我会一直使用它从类似字典的对象中获取项目:

if 'key' in mydict and mydict['key'] == 'heyyo!':
    do_stuff()

See @unutbu's answer for a fuller explanation.

有关更完整的解释,请参阅@unutbu 的回答。

回答by Pete Cacioppi

This isn't technically lazy evaluation, it's short-circuit boolean expressions.

这在技术上不是惰性求值,而是短路布尔表达式。

Lazy evaluation has a somewhat different connotation. For example, true lazy evaluation would likely allow this

惰性求值有一些不同的内涵。例如,真正的惰性求值可能会允许这样做

def foo(arg) :
    print "Couldn't care less"

foo([][0])

But Python doesn't.

但是 Python 没有。

Python is also nice in that it "echos" it's boolean arguments. For example, an or condition returns either it's first "truthy" argument or the last argument (if all arguments are "falsey"). An and condition does the inverse.

Python 也很不错,因为它“回显”了它的布尔参数。例如, or 条件返回它的第一个“真”参数或最后一个参数(如果所有参数都是“假”)。and 条件反之。

So "echo argument" booleans means

所以“回声参数”布尔值意味着

2 and [] and 1

2 和 [] 和 1

evaluates to [], and

计算为 [],并且

[] or 1 or 2

[] 或 1 或 2

evaluates to 1

评估为 1

回答by dansalmo

It is really the orpart that is short circuited:

确实or是短路的部分:

>>> 1 or 1/0  #also 0 and 1/0
1
>>> 0 or 1/0  #also 1 and 1/0

Traceback (most recent call last):
  File "<pyshell#1240>", line 1, in <module>
    0 or 1/0
ZeroDivisionError: integer division or modulo by zero

回答by Erik Veloso

Python's laziness can be proved by the following code:

Python 的懒惰可以通过以下代码来证明:

def foo():
    print('foo')
    return False

def bar():
    print('bar')
    return False

foo() and bar()         #Only 'foo' is printed

On the other hand,

另一方面,

foo() or bar()

would cause both 'foo' and 'bar' to be printed.

会导致 'foo' 和 'bar' 都被打印出来。

回答by Eric Wang

andoris lazy

andor很懒

&|is not lazy

&|不懒惰

回答by J.J

A short demo would be to compare the time difference between

一个简短的演示是比较之间的时间差

all(xrange(1,1000000000))

and

any(xrange(1,1000000000))

The all() has to check every single value, whilst the any() can give up after the first True has been found. The xrange, being a generator, therefore also gives up generating things as soon as the evaluator is done. For this reason, the all will consume large amounts of RAM and take ages, whilst the any will use just a few bytes and return instantaneously.

all() 必须检查每个值,而 any() 可以在找到第一个 True 后放弃。因此,作为生成器的 xrange 也会在评估器完成后立即放弃生成事物。出于这个原因, all 将消耗大量 RAM 并花费很长时间,而 any 将仅使用几个字节并立即返回。