itertools.ifilter与filter与list理解

2024-05-12 04:18:38 发布

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

我试图更熟悉itertools模块,并找到了一个名为ifilter的函数。

据我所知,它基于给定的函数过滤和iterable,并在包含iterable元素的列表上返回一个迭代器,该函数的计算结果为True

问题1我的理解迄今为止是否正确?

问题2:除了这个返回和迭代器之外,它与内置的filter函数有何不同?

问题3哪个更快?

据我所知,事实并非如此。我遗漏了什么吗?(我进行了以下测试)

>>> itertools.ifilter(lambda x: x%2, range(5))
<itertools.ifilter object at 0x7fb1a101b210>
>>> for i in itertools.ifilter(lambda x: x%2, range(5)): print i
... 
1
3
>>> filter(lambda x: x%2, range(5))
[1, 3]
>>> function = lambda x: x%2
>>> [item for item in range(5) if function(item)]
[1,3]

Tags: 模块lambda函数in元素列表forrange
3条回答

下面的示例包括一个数字生成器,它在生成数字之前立即打印消息,显示filter()如何首先构建列表,然后运行该列表并对其进行筛选。而itertools.ifilter则按原样过滤,从不构建列表。如果你要过滤500000个重要的东西,你需要ifilter,所以你不需要建立一个列表。

import itertools

def number_generator():
    for i in range(0, 3):
        print "yield", i
        yield i
    print "stopping"

function = lambda x: x > 0

numbers = number_generator()
print "itertools.ifilter:"
for n in itertools.ifilter(function, numbers):
    print n

print "\nfilter:"
numbers = number_generator()
for n in filter(function, numbers):
    print n

输出:

itertools.ifilter:
yield 0
yield 1
1
yield 2
2
stopping

filter:
yield 0
yield 1
yield 2
stopping
1
2

您的理解是正确的:唯一的区别是ifilter返回一个迭代器,而使用filter就像调用:

list(ifilter(...))

您可能还对PEP 289有关filter和ifilter的内容感兴趣:

List comprehensions greatly reduced the need for filter() and map(). Likewise, generator expressions are expected to minimize the need for itertools.ifilter() and itertools.imap(). [...]

还要注意,Python-3中的ifilter变成了filter(因此从itertools中删除)。

ifilter返回生成器,而不是列表。

生成器在需要时动态创建它们的项,而不是先分配整个列表。这是ifilterfilter之间的唯一区别

相关问题 更多 >