Jul*_*ian 6 python lambda tuples argument-unpacking iterable-unpacking
在 Python 中,按照惯例,下划线 ( _
) 通常用于丢弃解包元组的一部分,如下所示
>>> tup = (1,2,3)
>>> meaningfulVariableName,_,_ = tup
>>> meaningfulVariableName
1
Run Code Online (Sandbox Code Playgroud)
我正在尝试对 lambda 的元组参数执行相同的操作。只能用 2 元组来完成这似乎不公平......
>>> map(lambda (meaningfulVariableName,_): meaningfulVariableName*2, [(1,10), (2,20), (3,30)]) # This is fine
[2, 4, 6]
>>> map(lambda (meaningfulVariableName,_,_): meaningfulVariableName*2, [(1,10,100), (2,20,200), (3,30,300)]) # But I need this!
SyntaxError: duplicate argument '_' in function definition (<pyshell#24>, line 1)
Run Code Online (Sandbox Code Playgroud)
有什么想法吗?实现这一目标的最佳方法是什么?
正如注释中所示,只需使用加星号的参数将剩余的参数放入“_”中:
lambda x, *_: x*2
Run Code Online (Sandbox Code Playgroud)
如果您在语句中使用这些map
,因为 Python 不会将元组中的每个项目映射到不同的参数,您可以使用itertools.starmap
,这样做:
from itertools import starmap
result = map(lambda x, *_: x, [(0,1,2),])
Run Code Online (Sandbox Code Playgroud)
sort
但在关键参数or上没有等效的参数sorted
。
如果您不会在元组中间使用参数,只需对这些参数进行编号:
lambda x, _1, _2, _3, w: x*2 + w
Run Code Online (Sandbox Code Playgroud)
如果您收到某些 linter 工具关于未使用参数的投诉:linter 的目的是建议更具可读性的代码。我个人的偏好是不要让它妨碍实用性,如果发生这种情况,我会不假思索地关闭该行代码的 linter。
否则,你真的必须做“美丽”的事情——如果是为了取悦你和你的团队,或者仅仅是为了取悦 linter,那么只需运用良好的判断力。在这种情况下,它是编写一个完整的函数,并假装消耗未使用的参数。
def my_otherwise_lambda(x, unused_1, unused_2, w):
"""My make linter-happy docstring here"""
unused_1, unused_2 # Use the unused variables
return 2 * x + w
Run Code Online (Sandbox Code Playgroud)
除了 linter 存在问题之外,目的是让 lambda 参数可读,然后无论如何都建议拥有一个成熟的函数。lambda
为了保证可读性,v.3.0 中的语言确实很接近被剥夺。
最后但并非最不重要的一点是,如果元组中值的语义如此有意义,也许您应该考虑使用一个类来保存其中的值。通过这种方式,您可以将该类的实例传递给 lambda 函数,并通过它们各自的名称检查值。
Namedtuple 是一种效果很好的方法: from collections import nametuple
vector = namedtuple("vector", "x y z")
mydata = [(1,10,100), (2,20,200), (3,30,300)]
mydata = [vector(*v) for v in mydata]
sorted_data = sorted(mydata, lambda v: v.x * 2)
Run Code Online (Sandbox Code Playgroud)
小智 1
元组在 Python 中是不可变的,因此您无法“丢弃”(修改)无关的值。
此外,由于您不关心这些值是什么,因此绝对不需要将它们分配给变量。
我要做的就是简单地在您感兴趣的索引处索引元组,如下所示:
>>> list(map(lambda x: x[0] * 2, [(1,10,100), (2,20,200), (3,30,300)]))
[2, 4, 6]
Run Code Online (Sandbox Code Playgroud)
不需要*args
虚拟变量。
归档时间: |
|
查看次数: |
4894 次 |
最近记录: |