【问题标题】:How do I append a lambda to a list in python?如何将 lambda 附加到 python 中的列表?
【发布时间】:2019-09-02 21:03:58
【问题描述】:

我正在尝试制作一个程序来创建格式为y=mx+b 的 lambda 函数列表,其中“m”和“b”是预定值

我的总体目标是实现一个功能

  • 拍照
  • 找到上面的线条
  • 以纯色将它们扩展到整个图片

基本上,类似于 霍夫变换,如果你知道那是什么的话。

获得特定图像的线条后,我可以创建一个 lambda 函数来表示线条的斜率及其起点。我遇到了无法将 lambda 函数附加到列表的问题。

我已经试过了:

if __name__ == "__main__":
  nums = []
  for i in range(10):
    j = lambda x: x + i
    nums.append(j)
  for i in nums:
    print(i(1))

这是我得到的错误:

Traceback (most recent call last):
  File "C:/Users/me/.PyCharmCE2018.3/config/scratches/scratch_3.py", line 7, in <module>
    print(i(1))
  File "C:/Users/me/.PyCharmCE2018.3/config/scratches/scratch_3.py", line 4, in <lambda>
    j = (lambda x: x + i)
TypeError: unsupported operand type(s) for +: 'int' and 'function'

【问题讨论】:

标签: python lambda append


【解决方案1】:

您可以使用 operator.add 和 functools.partial 并且根本不使用 lambda:

import operator
import functools


if __name__ == "__main__":
    nums = []

    for i in range(10):
        nums.append(functools.partial(operator.add, i))
    for i in nums:
        print(i(1))

【讨论】:

    【解决方案2】:

    我认为您需要了解更多有关 lambda 函数的知识... 实际上,它的语法类似于:[lambda arguments: expression] 所以,问题是表达式中有两个变量,所以你需要传递两个参数。 我并没有真正得到你想要通过这个函数实现的目标,但我想你需要为 m 和 b 设置两个参数。

    在您的代码中,您需要初始化 x 并将其作为参数传递给 lambda。

                nums = []
                x=0
                for i in range(10):
                    j = lambda x,i : x + i
                    nums.append(j)
                for i in nums:
                    print(i(1,1))
    

    【讨论】:

      【解决方案3】:

      i 你的价值观变了,不是你想的那样。

      首先创建 lambda:

      j = lambda x: x + i
      

      希望 i 保持当前值(如 0、1、2 等)。

      然后你执行它:

      print(i(1))
      

      你知道你是如何命名你的第二个迭代器变量i的吗?将其更改为 j 并且您的示例将起作用。为什么?因为 python 在你的 lambda 中解析 i 的值,所以当你执行它时,而不是在你定义它的时候。因此,当您执行 lambda (i(1)) 时,它会转到您的 lambda 主体并尝试 x + i。然后它将查找 i,它现在包含您的 lambda(不是 INTEGER!)。因此你的问题。

      您需要执行双重功能才能使其正常工作。试试这个:

      if __name__ == "__main__":
        nums = []
        for i in range(10):
          def generate_lambda(i):
            return lambda x: x + i
          j = generate_lambda(i)
          nums.append(j)
        for i in nums:
          print(i(1))
      

      为什么会这样?当你调用 generate_lambda 时,会有一个带有你的 INTEGER 值的 i 变量。它将隐藏变量 i 稍后用于迭代 lambdas。而且由于您从不修改 generate_lambda 函数中的 i 变量,因此它将永远保持这种状态。

      【讨论】:

        【解决方案4】:

        这会给你一个线索:

        >>> i=1
        >>> a=lambda x:x+i
        >>> a(5)
        6
        >>> i=2
        >>> a(5)
        7
        

        lambda 在外部作用域中使用 i。在 OP 的情况下,所有的功能都是一样的。在最后一个循环中使用i 使i 成为一个函数,而不是一个整数。换成别的,你会发现功能都一样,用i的最后一个值:

        nums = []
        for i in range(10):
            j = lambda x: x + i
            nums.append(j)
        for f in nums:
            print(f(1))
        
        10
        10
        10
        10
        10
        10
        10
        10
        10
        10
        

        解决方法是,将i 设为函数的参数,以将值捕获为局部变量:

        nums = []
        for i in range(10):
            j = lambda x,i=i: x + i
            nums.append(j)
        for f in nums:
            print(f(1))
        
        1
        2
        3
        4
        5
        6
        7
        8
        9
        10
        

        【讨论】:

        • 是默认参数吗?聪明的方法:)
        • 哇,这太狡猾了。我喜欢。顺便说一句,非常感谢您的回答!
        【解决方案5】:

        问题是您创建的 lambdas 指的是活动堆栈帧中i 的当前值。当您稍后在第二个 for 循环中重用 i 时,它会绑定到列表中的 lambda。当以i(1) 调用时,lambdas 试图评估1 + i,其中i 是 lambda,所以你当然会得到一个错误。

        您可能想要的是在创建 lambda 时冻结 i 的值。您可以通过替换来做到这一点:

        j = lambda x: x + i
        

        与:

        j = (lambda y: lambda x: x + y)(i)
        

        这有效地捕获了i 的当前值,方法是将其绑定到一个 lambda 变量,然后立即应用该 lambda,之后绑定保持不变。

        【讨论】:

        • lambda x, i=i: x + i
        • @jonrsharpe 是的,我认为这也可以,尽管它允许传递第二个参数来覆盖捕获的 i 值。
        • 好吧,我的意思不是听起来很愚蠢,但我怎么能将它应用于需要 2 个变量的 lambda?就像我的 mx+b 函数,其中 x 是变化的东西,b 和 m 已经声明但会随着 for 循环中的每次迭代而变化?
        • 例如,如果你想捕获 3 个值,比如 i1i2i3,那么你可以这样做:j = (lambda y1, y2, y3: lambda x: x + y1 + y2 + y3)(i1, i2, i3)。当然,你可以在内部 lambda 中对它们做任何你想做的事情,但你明白了。
        • ```if name == "main": nums = [] j = 0 for i in range(10): j + = 1 H = (lambda y: lambda x: y)(j) L = (lambda y: lambda x: H(x) + y)(i) nums.append(L) for i in nums: print(i( 1))
        猜你喜欢
        • 2013-12-30
        • 1970-01-01
        • 2014-06-07
        • 2021-11-13
        • 1970-01-01
        • 1970-01-01
        • 2017-11-19
        • 2021-04-26
        • 1970-01-01
        相关资源
        最近更新 更多