我希望使用 itertools.chain
来高效地连接列表(记忆化),但我需要能够多次读取(或使用 map
等方法)结果。以下是一个例子,说明了这个问题:
import itertools
a = itertools.chain([1, 2], [3, 4])
print list(a) # => [1, 2, 3, 4]
print list(a) # => []
如何最好地避免这个问题?
我希望使用 itertools.chain
来高效地连接列表(记忆化),但我需要能够多次读取(或使用 map
等方法)结果。以下是一个例子,说明了这个问题:
import itertools
a = itertools.chain([1, 2], [3, 4])
print list(a) # => [1, 2, 3, 4]
print list(a) # => []
如何最好地避免这个问题?
与所有生成器一样,您需要将其转换为列表并存储该结果:
a = list(a)
这是生成器的一个基本原则,它们只能产生其序列一次。
此外,您不能仅仅为了记忆化而存储生成器,因为底层列表可能会发生变化。在几乎所有记忆化用例中,您应该存储列表;生成器通常仅用于高效地转换或过滤底层序列,并不代表您想要记忆化的数据本身。 这就像存储函数而不是其输出一样。对于您的特定情况,如果您所做的一切都是使用chain()
来连接现有列表,请直接存储这些列表。
请注意,这使生成器能够生成无限序列,因此要小心将其转换为列表。
尝试使用 itertools.tee:
import itertools
a = itertools.chain([1, 2], [3, 4])
a, b = itertools.tee(a)
print list(b) # => [1, 2, 3, 4]
a, b = itertools.tee(a)
print list(b) # => [1, 2, 3, 4]
list()
比使用tee()
更快。 - Paolo Moretti
list1 + list2 + ...
更高效的方法吗? - jtbandestimeit
来比较list(chain())
和list1 + ..
,但我猜测后者会更有效率。 - Martijn Pieters