from operator import itemgetter
from itertools import takewhile
xs = [ ('foo',1), ('bar',1), ('baz',2) ]在第二项上对xs进行排序-在'bar'之后没有更多的1。
def item_map(xs):
getcount = itemgetter(1)
return list(map(getcount,xs))
print(item_map(xs))
>>> [1, 1, 2]返回每个元组的第二个元素的列表。
def item_take(xs):
return list(takewhile(lambda x: x[1] == 1, xs))
print(item_take(xs))
[('foo', 1), ('bar', 1)]返回具有== 1的第二个元素的元组。
def could_this_work(xs):
match = itemgetter(1) == 1
return list(takewhile(match, xs))
print(could_this_work(xs))
TypeError: 'bool' object is not callable不返回具有== 1的第二个元素的元组
有没有办法用itemgetter代替lambda?或者itemgetter不能以这种方式使用?
编辑。使用takewhile是有原因的。我明白它的作用。此函数将在排序列表上使用。我很欣赏元组在这一点上是反向的,但我使用它的代码是正确的,符合我想要的和期望的。
发布于 2012-06-22 20:22:48
您的lambda函数实际上是由两个函数组成的:operator.itemgetter(1)和operator.eq。在纯函数风格中执行此操作将需要一个compose()函数,如下所示:
def compose(f, g):
def composed(x):
return f(g(x))
return composed使用此函数,您可以执行以下操作
from operator import itemgetter, eq
from functools import partial
def take_items(a):
return takewhile(compose(partial(eq, 1), itemgetter(1)), a)不过,我不认为这是一个好主意。我可能会选择直截了当
def take_items(a):
for x in a:
if x[1] != 1:
break
yield x我认为这不需要考虑代码的读者。
发布于 2012-06-22 20:18:33
尝试:
getcount = itemgetter(1)
match = lambda x: getcount(x) == 1您所做的是将itemgetter(1)修改为1。此比较返回False。那你就叫它。False(x)不能工作,因此会出现这个错误。
itemgetter(n)基本上是一个类似于:
def itemgetter(n):
return lambda x: x[n]您注意到返回另一个函数,将其与int进行比较毫无意义。
发布于 2012-06-22 20:20:28
itemgetter不做比较,它只是给你一个检索项目的函数。如果您想要进行比较,则需要创建自己的函数。
另外,请注意,您可以使用列表理解:
def could_this_work(xs):
return [x for x in xs if x[1] == 1]或者甚至是生成器表达式,它甚至可以在无限流上懒惰地工作:
def could_this_work(xs):
return (x for x in xs if x[1] == 1)(正如你的英语所说:获取第二个元素中有1的项。如果您想在找到非1元素时停止,请使用Sven的答案。)
https://stackoverflow.com/questions/11155957
复制相似问题