没有过滤和聚合(sum()等)的非空序列上的迭代器怎么可能不产生任何结果?
考虑一个简单的例子:
sequence = ['a', 'b', 'c']
list((el, ord(el)) for el in sequence)这会产生预期的[('a', 97), ('b', 98), ('c', 99)]。
现在,只需使用(...).next()将ord(el)替换为一个表达式,该表达式从某个生成器中取出第一个值--请原谅这个人为的示例:
def odd_integers_up_to_length(str):
return (x for x in xrange(len(str)) if x%2==1)
list((el, odd_integers_up_to_length(el).next()) for el in sequence)这就产生了[]。是啊,空名单。没有('a',填充)元组。没什么。
但我们不是在过滤、聚合或减少。没有过滤或聚合的n对象上的生成器表达式必须生成n对象,对吧?到底怎么回事?
发布于 2009-03-31 23:59:40
odd_integers_up_to_length(el).next()将引发StopIteration,它没有被捕获,但被捕获为其中的生成器表达式,停止它而不会产生任何结果。
看看第一次迭代,当值是‘a’时:
>>> odd_integers_up_to_length('a').next()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
StopIteration发布于 2009-04-01 00:01:30
发生的情况是,next()调用引发了一个StopIteration异常,该异常使堆栈向上冒泡到外部生成器表达式,并停止迭代。
StopIteration是迭代器表示它已经完成的正常方式。通常我们看不到它,因为通常情况下,next()调用发生在使用迭代器的构造中,例如for x in iterator或sum(iterator)。但是当我们直接调用next()时,我们就是负责捕获StopIteration的人。不这样做会导致抽象中的泄漏,这会导致外部迭代中的意外行为。
我想这给我们的教训是:在直接调用next()时要小心。
发布于 2009-04-01 00:03:10
str是保留关键字,您应该以不同的方式命名变量
我也想对下一步
https://stackoverflow.com/questions/703520
复制相似问题