所以我有一个数组,比如说[5,2,2,0]
,是否有一个函数可以返回通过标准的元素数量?
目前我正在这样做:
a = [5,2,2,0]
len([i for i in a if i > 0])
也有人提出了这种方法:
sum(b > 0 for b in a)
但 IMO 这真的是一回事,只是可读性差了一点。
有没有这样的方法我可以使用:
def crit(x): return x > 0
a.count(criterion=crit)
所以我有一个数组,比如说[5,2,2,0]
,是否有一个函数可以返回通过标准的元素数量?
目前我正在这样做:
a = [5,2,2,0]
len([i for i in a if i > 0])
也有人提出了这种方法:
sum(b > 0 for b in a)
但 IMO 这真的是一回事,只是可读性差了一点。
有没有这样的方法我可以使用:
def crit(x): return x > 0
a.count(criterion=crit)
你能做的不多,但如果你已经有了你的谓词
def crit(x):
return x > 0
你可以做
sum(map(crit, a))
或者
len(filter(crit, a))
len([x for x in a if x > 0])
是最有效的,但如果您想重用谓词,可能会导致代码重复。
测试:
In [6]: %timeit len([x for x in a if x > 0])
100000 loops, best of 3: 3.57 us per loop
In [7]: def crit(x):
...: return x > 0
...:
In [8]: %timeit len([x for x in a if crit(x)])
100000 loops, best of 3: 10.1 us per loop
In [9]: %timeit sum([x > 0 for x in a])
100000 loops, best of 3: 5.66 us per loop
In [10]: %timeit sum([crit(x) for x in a])
100000 loops, best of 3: 12 us per loop
In [11]: %timeit sum(map(crit, a))
100000 loops, best of 3: 11.3 us per loop
In [12]: %timeit len(filter(crit, a))
100000 loops, best of 3: 8.21 us per loop
生成器(生成器没有len
):
In [13]: %timeit sum(1 for x in a if x > 0)
100000 loops, best of 3: 3.99 us per loop
In [14]: %timeit sum([1 for x in a if crit(x)])
10000 loops, best of 3: 10.6 us per loop
In [15]: %timeit sum(x > 0 for x in a)
100000 loops, best of 3: 6.24 us per loop
In [16]: %timeit sum(crit(x) for x in a)
100000 loops, best of 3: 13 us per loop
imap
比map
:
In [17]: %timeit sum(itertools.imap(crit, a))
100000 loops, best of 3: 10.7 us per loop
在测试了所有这些之后,我想我会选择 [13]、[17] 或 [14]。
我会采用这种sum
方法而不是具体化一个列表 - 如果你觉得它太可怕了,只需编写一个辅助函数:
def count_if(f, iterable):
return sum(1 for i in iterable if f(i))
或者更好的是,使用itertools 文档中的一种方法:
def quantify(iterable, pred=bool):
"Count how many times the predicate is true"
return sum(imap(pred, iterable))
你可以使用filter
函数len(filter(crit, a))