繁体   English   中英

生成器函数在列表和生成器表达式上的行为不同?

[英]Generator function behaving differently on lists and generator expressions?

所以我写了这个无用的生成器函数,它消耗了迭代器的前 4 个元素:

def f(it):
    for _ in range(2):
        for _, x in zip(range(2), it):
            yield x

如我所料,以下示例:

y = (x for x in range(4))
for x in f(y):
    print(x)
0
1
2
3

这个例子让我感到困惑:

for x in f([0, 1, 2, 3]):
    print(x)
0
1
0
1

为什么两个输出不同?

列表是可迭代的,但不是迭代器 如果在传递之前从列表中创建迭代器,您将看到与生成器表达式相同的行为:

>>> list(f(iter([0, 1, 2, 3])))
[0, 1, 2, 3]

迭代器被迭代消耗,所以当你第二次zip时,你是通过迭代器的一部分:

>>> i = iter([0, 1, 2, 3])
>>> zip(range(2), i)
[(0, 0), (1, 1)]
>>> zip(range(2), i)
[(0, 2), (1, 3)]
>>> zip(range(2), i)
[]

但是当你zip列表时,你会再次启动它,创建一个新的迭代器:

>>> l = [0, 1, 2, 3]
>>> zip(range(2), l)
[(0, 0), (1, 1)]
>>> zip(range(2), l)
[(0, 0), (1, 1)]
>>> zip(range(2), l)
[(0, 0), (1, 1)]

那是因为列表不是迭代器,它是一个列表。 在第一种情况下发生的是它正在消耗迭代器。 在第二种情况下,它是从头开始。 您需要执行iter([0, 1, 2, 3])

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM