我想从列表列表的所有子列表中获取第i个元素。我尝试使用map和lambda函数,如下所示
extract = lambda x,i :x[i]
a = [[1,2,3],[4,5,6],[6,7,8]]
b = list(map(extract(i = 1),a))
我希望b为[2,5,7] 但我知道最后一行不起作用。我应该如何使用map和lambda来解决这个问题
答案 0 :(得分:2)
您可以在1
中进行硬编码:
extract = lambda x: x[1]
a = [[1,2,3],[4,5,6],[6,7,8]]
b = list(map(extract,a))
print(b)
# [2, 5, 7]
您通常不希望将lambda
存储到变量中,这样更好:
def extract(x):
return x[1]
b = list(map(extract, a))
或者简单地说:
b = list(map(lambda x: x[1], a))
您还可以使用列表理解,我个人认为这是最佳选择:
c = [x[1] for x in a]
print(b == c)
True
答案 1 :(得分:2)
潜在的 问题是调用extract
时需要指定第一个函数参数。可以通过functools.partial
:
from functools import partial
b = list(map(partial(extract, i=1), a)) # [2, 5, 7]
但这相对来说效率不高,因为会为a
的每次迭代创建一个新函数。如其他人所建议,改为使用operator.itemgetter
:
from operator import itemgetter
b = list(map(itemgetter(1), a)) # [2, 5, 7]
顺便说一句,PEP 8建议不要命名lambda
函数;而是明确定义:
def extract(x, i):
return x[i]
答案 2 :(得分:1)
我建议在此处使用operator.itemgetter
来获取每个子列表的第二项:
from operator import itemgetter
a = [[1,2,3],[4,5,6],[6,7,8]]
print(list(map(itemgetter(1), a)))
# [2, 5, 7]
或使用lambda
:
a = [[1,2,3],[4,5,6],[6,7,8]]
print(list(map(lambda x: x[1], a)))
# [2, 5, 7]
您的匿名功能:
extract = lambda x,i :x[i]
需要专门映射索引:
extract = lambda x: x[1]
然后,您可以使用map(extract(1), a)
将此功能简单地映射到您的列表。
答案 3 :(得分:1)
您不需要,无需对索引进行硬编码。
恕我直言,您应该通过执行以下操作从extract
方法返回一个lambda函数:
def extract(i):
return lambda x : x[i]
a = [[1,2,3],[4,5,6],[6,7,8]]
b = list(map(extract(1), a))
print(b)
输出:
[2, 5, 7]
注意:更好的(阅读pythonic)方法将是使用列表理解:
a = [[1,2,3],[4,5,6],[6,7,8]]
b = [li[1] for li in a]
print(b)
答案 4 :(得分:0)
我也投票赞成“赞成”解决方案。 函数式编程语法看起来很漂亮,但有时开销太大。
a = [[1,2,3],[4,5,6],[6,7,8]]
b = list(map(lambda x: x[1], a)) # Brr, how many types conversions involved
c = [x[1] for x in a] # Looks more lightweight
让我们检查一下:
import timeit
timeit.timeit('a = [[1,2,3],[4,5,6],[6,7,8]]; b = [x[1] for x in a]', number=10000)
> 0.01244497299194336
timeit.timeit('a = [[1,2,3],[4,5,6],[6,7,8]]; b = list(map(lambda x: x[1], a))', number=10000)
> 0.021031856536865234
慢2倍。