Python Tkinter 函数间传递变量
我想把变量 dirpath 传递给 export_data() 这个函数。export_data 是在一个小部件上的按钮被双击时运行的。为什么 dirpath 打印出来的是:
`<Tkinter.Event instance at 0x8ade56c>`
而不是实际的路径呢?
def export_data(dirpath):
print 'exporting...'
print str(dirpath)
os.mkdir('/home/bigl/Desktop/Library')
shutil.copytree(dirpath, output_path)
当我运行我的代码时,我得到了这个错误:
exporting...
<Tkinter.Event instance at 0x8ade56c>
Traceback (most recent call last):
File "/usr/lib/python2.7/lib-tk/Tkinter.py", line 1413, in __call__
return self.func(*args)
File "/media/LOFTUS/20130308_searchtest.py", line 44, in export_data
shutil.copytree(dirpath, output_path)
File "/usr/lib/python2.7/shutil.py", line 169, in copytree
names = os.listdir(src)
TypeError: coercing to Unicode: need string or buffer, instance found
2 个回答
0
显然,Tkinter
传递的是一个事件,而不是一个字符串,给你的回调函数。如果 dirpath
是一个全局变量(就像你之前写的那样——这很重要!),也许你应该这样定义你的回调函数:
def export_data(_ignored):
print 'exporting...'
print str(dirpath)
os.mkdir('/home/bigl/Desktop/Library')
shutil.copytree(dirpath, output_path)
现在你的函数可以使用全局的 dirpath
(还有 output_path
)。你之前的写法中,参数的声明遮住了同名的全局变量。
1
在你提问的内容中:
你提到:导出数据是通过双击一个小部件上的按钮来触发的。为什么 dirpath 打印出来是:
<Tkinter.Event instance at 0x8ade56c>
当你绑定一个事件时,这个绑定总是会把一个事件对象作为参数传递给绑定的函数。所以,如果你这样写:
widget.bind("<Double-1>", export_data)
...那么 export_data
函数就会接收到这个事件作为它唯一的参数。
如果你想传递一个变量,你需要使用 lambda
或者 functools.partial
,或者其他一些函数生成器。比如:
widget.bind("<Double-1>", lambda event: export_data(dirpath))
不过要小心,这样做的话,传递给 export_data
的值将是 dirpath
在事件发生时的值,这个值可能和你创建绑定时的值不同。
如果你有一个局部变量想要传递给函数,可以把它设置为一个关键字参数的默认值,这样在创建 lambda
时的值就会被传递。
举个例子:
path = some_function()
widget.bind("<Double-1>", lamba event, dirpath=path: export_data(dirpath))