日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > python >内容正文

python

python退出mainloop_不要阻塞tkinter的mainloop

發布時間:2025/3/15 python 31 豆豆
生活随笔 收集整理的這篇文章主要介紹了 python退出mainloop_不要阻塞tkinter的mainloop 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

最近被GUI多線程代碼的死鎖問題搞的有點頭大,本文總結一下自己的所思所得,并不代表完全正確,因為畢竟沒有去閱讀tk的源代碼。

mainloop,故名思議,它就應該是python程序的mainThread。這個GUI的mainloop,靠事件響應驅動。比如有一個button(A),點A,就是給這個mainloop傳遞了一個事件,這個事件最后會傳遞到A綁定的commnad函數中去執行。

不要阻塞tkinter的mainloop,就是不要在事件響應的函數中阻塞住,否則GUI會卡死。常見的現象是,A綁定的函數執行需要那么一點點時間,點擊下去后,GUI就會卡住那么一點點時間。所以,大多數編程教材都建議使用多線程來規避GUI的卡死,即點擊A后啟動一個線程,A綁定的函數立即返回,釋放GUI(表示GUI有可能接收別的事件的響應了),具體工作由線程完成。

由線程來完成工作,并規避GUI的卡死,是個很好的最佳實踐,不過,我遇到的問題是,線程被GUI卡死了!

計算模型大概是這樣的:多個線程通過操作一個Text控件就是往里寫log;寫log的執行流程代碼中,有mutex,用來多線程間控制Text的狀態;GUI的事件響應中,也有mutex.acquire;只要GUI出發這個事件,整個程序就死鎖了。

為什么會這樣呢?我想來想去,覺得出問題的地方,就是線程被GUI卡死了。為什么線程會被卡死呢?因為線程在mutex.acquire中在向GUI發事件(操作Text),而此時GUI在等待mutex,于是死鎖。

GUI在一個事件沒有處理完的情況下,是無法處理別的事件的。比如我們在A的綁定函數中sleep,整個GUI上其它地方都點不了(OS會記錄這些事件,在GUI被釋放后再把這些事件灌給它)。線程中對Text的操作無法返回,很可能就是因為GUI已經被卡死了。

奇怪的是,如果A綁定代碼中也操作Text,不會卡死,而只是在GUI被釋放后,一口氣把所有的log全顯示出來,log顯示的過程只是感覺不流暢而已。區別在于mainloop中觸發事件和非mainloop中觸發(我個人的理解哈),也許存在內部事件和外部事件這樣的區別,外部事件會被阻塞,即線程操作Text的代碼被阻塞,而mainloop中操作Text的代碼,只是更新延后。

總之,在GUI中如果有mutex.acquire這樣的代碼,是非常危險的,一不留神就死鎖。不要阻塞mainloop的事件響應,用線程是OK的,用戶友好。多線程之間有mutex沒問題,只要GUI的mainloop沒有被卡死。

-- EOF --

總結

以上是生活随笔為你收集整理的python退出mainloop_不要阻塞tkinter的mainloop的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。