我有一个相当复杂的tkintergui,所以避免重复使用lambda函数分配控件是值得的。代码摘录如下:
def createRightMenu(self, treeName, commands: []):
for cmd in commands:
self.rightMouse[treeName].add_command(label= cmd['label'], command= lambda: self.execCommand(cmd['reqId']))
self.tree[treeName].bind("<Button-3>", lambda event:
self.rightMouse_click(event.x_root, event.y_root, treeName))
def execCommand(self, reqId):
print("execCommand", reqId)
self.tree = {}
treeName = 'a'
self.createTree(root, treeName)
self.createRightMenu(treeName , [
{'label': 'copy', 'reqId': 1},
{'label': 'retrieve', 'reqId': 2},
])
什么有用? 在我的右击菜单中,我得到“copy”和“retrieve”两个条目,并调用execCommand
什么不起作用? execCommand总是获取最后一个列表元素,即“retrieve”,2作为参数,即使我右键单击“copy”。如果我手动添加两个。add\u命令就可以了。只使用for循环是行不通的。知道为什么吗
作用域问题:当
lambda
激发时,它检查cmd
变量的作用域。在for cmd in commands:
的每次迭代过程中,cmd
变量被设置为一个新值。在迭代结束时,中的cmd
变量仍然等于for cmd in commands:
的最终迭代(即-{'label': 'retrieve', 'reqId': 2}
)解决方案是在
lambda
的签名中指定一个“new”变量,然后根据python中作用域的工作方式使用它(在“new”上加引号,因为它可以是同名的变量)。具体来说,您可以将代码更改为:下面是一个脚本,通过示例演示我在这里所说的内容:
以下是一些链接:
相关问题 更多 >
编程相关推荐