对包含print()的生成器调用any()会产生意外的行为

2024-06-28 19:19:00 发布

您现在位置:Python中文网/ 问答频道 /正文

any一旦在任何iterable(无论是迭代器、生成器、列表等)中找到一个truthy值,就应该短路

对于普通发电机,这是正确的:

Python 3.6.2 (v3.6.2:5fd33b5, Jul  8 2017, 04:14:34) [MSC v.1900 32 bit (Intel)] on win32  
Type "help", "copyright", "credits" or "license" for more information.
>>> gen = (i for i in range(100))
>>> gen
<generator object <genexpr> at 0x0341A360>
>>> next(gen)
0                         
>>> next(gen)
1   
>>> any(gen)
True                                                                                       
>>> next(gen)
3                                      
>>>

如果创建的generate包含print,则any不会短路:

>>> gen = (print(i) for i in range(100))
>>> next(gen)
0
>>> next(gen)
1
>>> any(gen)
2
3
4
5
6
7
8
9
...

为什么添加print会防止any短路


Tags: in列表forbitanyrangeiterablejul
1条回答
网友
1楼 · 发布于 2024-06-28 19:19:00

函数print()返回None。考虑这一点:

>>> gen = (print(i) for i in range(10))
>>> list(gen)
0
1
2
3
4
5
6
7
8
9
[None, None, None, None, None, None, None, None, None, None]

您可以看到生成器为每个迭代返回None

any()运行,直到找到真实值。因为None从来都不是真实的,any()运行到完成

您可以通过确保生成器返回每次迭代的预期值来挽救原始代码:

>>> gen = (print(i) or i for i in range(10))
>>> next(gen)
0
0
>>> next(gen)
1
1
>>> any(gen)
2
True

相关问题 更多 >