循环中的Lambda存储在列表中,仅打印最后一个循环的评估值,而不是所有循环迭代中的不同值

低:

我在循环中遇到lambda问题。很难解释这个问题,所以我将在一个简短的例子中展示它:

class TestObj():
    def __init__(self, value):
        self.value = value

lambdas = []
values_list = [10, 1]
for ele in values_list:
    foo = TestObj(ele)
    lambdas.append(lambda: foo.value > 5)

print([single_lambda() for single_lambda in lambdas])

由于打印,我得到:

[False, False]

尽管我期望[True,False]。你能告诉我为什么它不起作用吗?以及如何获得预期的结果?我仅补充说,在我的代码中需要lambda循环来定义公式(这些公式很多,而且可能更复杂)。这些公式在应用程序中的一个位置定义,并在定义下方的许多行之后执行。谢谢您的帮助。

帕特里克·阿特纳(Patrick Artner):

Lambda在执行时会进行评估。

当您打印它们时将执行它们。foo那时唯一已知的是最后一个循环中的那个。因此TestObj(1)被打印两次。

您可以通过将lambda更改为:

lambdas.append(lambda: id(foo))   # will print the id() of the used foo

您需要“尽早”将foo循环中的绑定到lambda:

lambdas.append(lambda x = foo: x.value > 5) # bind x to foo from loop, check x.value

完整修复:

class TestObj():
    def __init__(self, value):
        self.value = value

lambdas = []
values_list = [10, 1]
for ele in values_list:
    foo = TestObj(ele)
    # use an x and bind it to this loops foo
    lambdas.append(lambda x = foo: x.value > 5)

# this is bad btw, use a simple for loop - do not use a list comp to create a list
# simply to print values 
print([single_lambda() for single_lambda in lambdas]) 

输出:

[True, False]

# and for the changed lambda with id() : the same id() twice

请参阅仅使用列表推导来产生副作用是Pythonic吗?关于使用列表理解的副作用以及它为什么不好的问题。


有关:

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章