这是我的问题的一个小实现。当我点击“按下”按钮时,它会挂起,而有些时候则没有。怎么能克服这个悬念? 这是我的代码。
安装Sane“sudo apt-get install python-imaging-sane”
import gtk
import gtk.glade
import threading
import os
import sane
gtk.gdk.threads_init()
class process(threading.Thread):
def __init__(self,main_object):
self.main_object = main_object
threading.Thread.__init__(self)
def run(self):
sane_version = sane.init()
sane_devices = sane.get_devices()
gtk.threads_enter()
self.main_object.pb.set_fraction(self.main_object.value)
gtk.threads_leave()
self.main_object.value = self.main_object.value + .1
class main():
def __init__(self):
#GUI
window = gtk.Window()
window.set_default_size(200,200)
vbox = gtk.VBox(False,0)
self.pb = gtk.ProgressBar()
button = gtk.Button("Press me ")
button.connect("clicked",self.fun_to_call)
vbox.pack_end(self.pb)
vbox.pack_end(button)
button.show()
self.pb.show()
vbox.show()
window.add(vbox)
self.value = .1
window.show()
def fun_to_call(self,data=None):
pro = process(self)
pro.start()
main()
gtk.main()
答案 0 :(得分:0)
看PyGTK FAQ on the subject,你似乎错过了一步; (整个FAQ条目虽然很有意思)
...你必须使用gtk.threads_enter()/ gtk.threads_leave()包装主循环,如下所示:
gtk.threads_enter()
gtk.main()
gtk.threads_leave()
他们也有一些建议如何使用finally
来确保即使代码抛出异常也始终运行gtk.threads_leave()
。
请注意,虽然使用这种GUI线程不一定是可移植的,但某些操作系统可能会遇到非主线程运行GUI操作的问题,即使正确锁定也是如此。
答案 1 :(得分:0)
标准python实现(“cpython”)的内部不是线程安全的。
因此锁(Global Interpreter Lock)用于确保一次只运行一个python线程。这个锁被释放,例如当正在运行的线程执行I / O时。但是如果没有释放锁,其他线程将无法运行。
我怀疑这是问题的根源。这取决于理智绑定的实现。
您可以尝试使用multiprocessing
模块而不是threading
。多处理为长时间运行的任务启动一个完全不同的过程,因此它不受GIL的约束。但您必须使用multiprocessing
提供的工具,例如Queue
和Pipe
,以便在流程之间交换信息。