【问题标题】:Python lambda function underscore-colon syntax explanation?Python lambda 函数下划线冒号语法解释?
【发布时间】:2016-10-10 22:21:26
【问题描述】:

在“aDict”是字典的以下 Python 脚本中,“_: _[0]”在 lambda 函数中做了什么?

sorted(aDict.items(), key=lambda _: _[0])

【问题讨论】:

  • _ 只是一个变量。它根据字典的第一项对它们进行排序。
  • 小扩展,即_ 可能是my_varfoo,或woo。就像@AndrewL。说,它只是一个变量名。
  • 该键对于该特定代码也没有任何作用。
  • 这也没用,你在哪里看到的?
  • @PadraicCunningham:我在别人的代码中看到了。

标签: python sorting lambda key


【解决方案1】:

让我们把它分开。

1) 假设你有一个 dict,di:

di={'one': 1, 'two': 2, 'three': 3}

2) 现在假设您想要它的每个键值对:

 >>> di.items()
 [('three', 3), ('two', 2), ('one', 1)]

3) 现在你想对它们进行排序(因为 dicts 是无序的):

>>> sorted(di.items())
[('one', 1), ('three', 3), ('two', 2)]

请注意,元组是按字典顺序排序的——按元组第一个元素中的文本。这相当于一系列元组的t[0]

假设您希望它按数字排序。你会使用key 函数吗:

>>> sorted(di.items(), key=lambda t: t[1])
[('one', 1), ('two', 2), ('three', 3)]

你有sorted(aDict.items(), key=lambda _: _[0]) 的语句只是使用_ 作为变量名。它也不做任何事情,因为aDict.items() 产生元组,如果你没有使用键,它无论如何都会按元组的第一个元素排序。您示例中的关键功能完全没用。

可能需要考虑表单的用例(元组除外)。如果您有字符串,那么您将按第一个字符排序并忽略其余字符:

>>> li=['car','auto','aardvark', 'arizona']
>>> sorted(li, key=lambda c:c[0])
['auto', 'aardvark', 'arizona', 'car']

对比:

>>> sorted(li)
['aardvark', 'arizona', 'auto', 'car']

但是,我仍然不会在 lambda 中使用 __ 的使用是用于副作用可能性最小的一次性变量。 Python 有命名空间,主要是让这种担心不再是真正的担心。

考虑:

>>> c=22
>>> sorted(li, key=lambda c:c[0])
['auto', 'aardvark', 'arizona', 'car']
>>> c
22

c 的值由于lambda 内的本地命名空间而得以保留。

然而(在 Python 2.x 而非 Python 3.x 下)这可能是个问题:

>>> c=22
>>> [c for c in '123']
['1', '2', '3']
>>> c
'3'

因此,(轻量级)约定变成了在列表理解或元组扩展等情况下对变量使用_,在这种情况下,您不必担心践踏您的名字。消息是:如果它被命名为_,我真的不在乎它,除了这里......

【讨论】:

    【解决方案2】:

    在 Python 中_(下划线)是一个有效的标识符,可以用作变量名,例如

    >>> _ = 10
    >>> print(_)
    10
    

    因此它也可以用作 lambda 表达式的参数名称 - 这就像一个未命名的函数。

    在您的示例中,sorted()aDict.items() 生成的元组传递给它的key 函数。 key 函数返回该元组的第一个元素,sorted() 然后将其用作键,即与其他值进行比较以确定顺序的值。

    注意,在这种情况下,没有键函数也可以产生相同的结果,因为元组自然是根据第一个元素排序,然后是第二个元素,等等。所以

    sorted(aDict.items())
    

    将产生相同的结果。因为字典不能包含重复键,每个元组的第一个元素是唯一的,所以排序时从不考虑第二个元素。

    【讨论】:

      【解决方案3】:

      在 Python 中,lambda 用于创建匿名函数。您示例中的第一个下划线只是 lambda 函数的参数。在冒号(即函数签名)之后,_[0] 检索变量 _ 的第一个元素。

      诚然,这可能会令人困惑;您的示例的 lambda 组件可以重写为 lambda x: x[0] 并具有相同的结果。但是,按照惯例,Python 中的下划线变量名用于“一次性变量”。在这种情况下,这意味着我们在每个字典项中唯一关心的是键。细微的差别,也许。

      【讨论】:

      • 注意:_ 也用作gettext 或类似函数的别名来检索消息以进行国际化。但那是另一个故事。尽管如此,下划线可能会影响另一个下划线,因此最好使用“真实”变量名。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2013-08-28
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-08-09
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多