【问题标题】:Is this the correct way to use the lambda and map function to execute this piece of code [duplicate]这是使用 lambda 和 map 函数执行这段代码的正确方法吗?
【发布时间】:2021-07-29 07:12:46
【问题描述】:

在执行这段代码时,我的理解出现了这种困惑或差距。我尝试了几种方法来解决这个问题,但我无法这样做。解决这个问题的正确方法是什么。

find_max = map(lambda a, b, c: a if a > b and a > c
                   else (b if b > a and b > c else c), (2, 3, 4))
print(list(find_max))

我收到以下错误

Traceback (most recent call last):
  File "<input>", line 1, in <module>
TypeError: <lambda>() missing 2 required positional arguments: 'b' and 'c'

我调整了上面的代码

find_max=map(lambda a:a[0] if a[0]>a[1] and a[0]>a[2] 
    else (a[1] if a[1]>a[0] and a[1]>a[2] else a[2]),(2,3,4))
print(list(find_max))

我收到以下错误

Traceback (most recent call last):
  File "<input>", line 1, in <module>
  File "<input>", line 1, in <lambda>
TypeError: 'int' object is not subscriptable

然后我进一步调整

find_max=map(lambda *a:a[0] if a[0]>a[1] and a[0]>a[2] 
    else (a[1] if a[1]>a[0] and a[1]>a[2] else a[2]),(2,3,4))
print(list(find_max))
``

I got the below error

    Traceback (most recent call last):
      File "<input>", line 1, in <module>
      File "<input>", line 1, in <lambda>
    IndexError: tuple index out of range

【问题讨论】:

  • 你能显示预期的输出,你的元组/字典/列表
  • map 接受一个可调用对象,该可调用对象将提供一个单个参数
  • find_max 似乎想在可迭代对象中找到最大值。这根本不是map 的用例。 Map 接受一个可迭代对象并将一个函数应用于每个元素,即它将函数映射到 iterable 的元素上。迭代器本身将始终具有与原始迭代器一样多的元素。你根本不想在这里使用map
  • 请注意,您实际上根本没有解释您要完成的工作,让我们猜测,实际上不应该是这样,您应该始终提供完整的问题陈述。

标签: python python-3.x dictionary lambda


【解决方案1】:

你不想在这里使用map,你只想调用这个函数:

(lambda a, b, c: a if a > b and a > c else (b if b > a and b > c else c)) (2, 3, 4)

如果你 map 到例如你的第二个调整可以工作。包含单个三元组的列表:

list(map(lambda a:a[0] if a[0]>a[1] and a[0]>a[2] else (a[1] if a[1]>a[0] and a[1]>a[2] else a[2]),[(2,3,4)]))
# returns [4]

【讨论】:

  • 但是这太荒谬了
  • @juanpa.arrivillaga 'absurd' as '为什么不直接使用max?我认为这只是一个练习......
  • 就像创建一个匿名函数只是为了立即调用它。 map 的用法也很荒谬,它不是map 的正确用法。当人们问一个问题,“我怎么射自己的脚”,你应该回答,“不要射自己的脚”。
【解决方案2】:

当您调用map(fn, iterable) 时,它会在iterable 的每个单个元素 上调用给定的fn。这意味着您的lambda 依次在234 上被调用;它永远不会同时将它们三个都作为参数。

实际上不可能将“查找最大值”操作作为对map 的调用来实现,因为您最终想要获得一个结果,而map 将为输入可迭代的每个元素提供一个结果.

简单的解决方案当然是使用内置的max()函数:

>>> max((2, 3, 4))
4

如果您想实现自己的max 版本,您可能不想使用maplambda,因为找到最大值需要您在跟踪最大元素的同时遍历所有元素(意味着它需要一个局部变量和一个循环,这两者在 lambda 中都很难实现):

>>> def find_max(iterable):
...     m = None
...     for i in iterable:
...         if m is None or m < i:
...             m = i
...     return m
...
>>> find_max((2, 3, 4))
4

【讨论】:

    【解决方案3】:

    这里根本不想使用map。您试图在可迭代中找到最大值,这不是映射操作,而是减少。如果你想使用函数式编程原语,你正在寻找reduce:

    >>> from functools import reduce
    >>> reduce(lambda acc, x: x if x > acc else acc, (2, 3, 4))
    4
    

    当然,您可以只使用内置的max,这是您应该使用的。即使你要实现这样的东西,一个简单的循环实现也更符合习惯(当然,这是风格问题)。

    【讨论】:

      【解决方案4】:

      请注意,map 将操作每个元素。 在第一个示例中,您犯了两个错误。

      map(lambda ...., (2, 3, 4)),在本例中,python 尝试为每个元素执行 lambda 函数,例如 lambda 2, ?, ?: xxlambda 3, ?, ?: xxlambda 4, ?, ?: xx。(这就是它给你的原因:&lt;lambda&gt;() missing 2 required positional arguments: 'b' and 'c'

      首先,您可能需要将元组列表传递给map

      还要注意,python 已经删除了Tuple Parameter Unpacking

      所以方式(不会引发异常,但很奇怪):

      find_max=map(lambda a:a[0] if a[0]>a[1] and a[0]>a[2] 
          else (a[1] if a[1]>a[0] and a[1]>a[2] else a[2]),[(2,3,4)])
      print(list(find_max))
      

      不过,没有必要使用map

      【讨论】:

        【解决方案5】:

        试试这个:

        find_max = map(lambda a:a[0] if (a[0]>a[1] and a[0]>a[2]) 
                       else (a[1] if a[1]>a[0] and a[1]>a[2] 
                       else a[2]), [[2,3,4]])
        

        参数必须是列表中的列表。

        【讨论】:

        • 但这太荒谬了
        • 确实是这样,但我不是来评判的。只是想帮忙。
        • 向人们展示如何以错误的方式做事是没有帮助的
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2010-09-16
        • 2015-12-07
        • 1970-01-01
        • 1970-01-01
        • 2015-11-24
        • 2015-09-21
        • 2013-04-25
        相关资源
        最近更新 更多