帶界面的Python程序,當底層函數運行時間過長,這時界面就會產生卡死的現象,體驗極差。
1 def do_test(self, event): 2 print("Test Begin!!!") 3 4 test_run() 5 6 print("Test Over!!!") 7 8 #底層需要執行的函數 9 def test_run() 10 time.sleep(60)
上面這段代碼在執行過程中,界面會卡死60s,只有等 test_run()執行完成后才能恢復正常。
所以應該給底層函數test_run()重新開辟一個線程,這樣就能解決界面卡死的現象了
1 class MyThread(Thread): 2 def __init__(self, 3 parent=None): 4 Thread.__init__(self) 5 6 def run(self): 7 test_run() 8 9 def do_test(self, event): 10 print("Test Begin!!!") 11 #創建新線程 12 testthread = MyThread(parameter_a, parameter_b) 13 #運行底層函數 14 testthread.start() 15 16 print("Test Over!!!") 17 18 #底層需要執行的函數 19 def test_run() 20 time.sleep(60)
但這里又出現一個問題,子線程test_run()函數還沒執行完成,主進程 do_test()已經全部執行結束了,“Test Over!”已經心安理得的打印出來了,這就尷尬了!
找了一些方法,比如 在 testthread.start()代碼后加一句 testthread.join(),這句話的作用是等待test_run()執行完成后才繼續執行do_test(),但是這樣運行結果跟第一段代碼一樣了,界面還是會卡死!!!
所以解決該問題,我用了以下方法:
第一步:子線程中添加代碼,當子線程執行完畢后通知主進程
#發送信息“Over”給主進程
wx.CallAfter(pub.sendMessage,"Over",msg="Thread finished!")
第二步 :主進程中添加接受消息代碼塊:
#主進程接受到消息“Over”后執行函數“task_over”
pub.subscribe(self.task_over,"Over")
完整代碼如下:
1 class MyThread(Thread): 2 def __init__(self, 3 parent=None): 4 Thread.__init__(self) 5 6 def run(self): 7 test_run() 8 #執行完test_run()后給主進程發送“Over”信息 9 wx.CallAfter(pub.sendMessage,"Over",msg="Thread finished!") 10 11 def do_test(self, event): 12 print("Test Begin!!!") 13 #創建新線程 14 testthread = MyThread(parameter_a, parameter_b) 15 #運行底層函數 16 testthread.start() 17 18 #接收到“Over”信息后,執行task_over函數 19 pub.subscribe(self.task_over,"Over") 20 21 def task_over() 22 print("Test Over!!!") 23 24 #底層需要執行的函數 25 def test_run() 26 time.sleep(60)
這樣就解決print打印信息的問題。