2011-08-15 20 views
5

我剛剛在程序中發現了一個與其使用Python的多處理模塊有關的奇怪錯誤。當我在機器上從源代碼運行程序時,一切正常。但我一直在使用pyinstaller將其構建爲可執行文件,出於某種原因,當我運行由我的代碼構建的可執行文件時,多處理的行爲發生了巨大變化。特別是,當我嘗試運行我的代碼的多處理部分,而不是按照它應該做的時候,看起來是我的程序主窗口的副本彈出,每個進程一個彈出。更糟糕的是,如果它們手動關閉,它們會重新打開,大概是因爲它們是多處理池的一部分。沒有錯誤信息被打印,並且一旦創建完畢,所有的窗口就會坐在那裏無所事事。可能會發生什麼導致這種情況?Python - Multiprocessing.processes從可執行文件運行時變成主進程的副本

+2

發現它 - 顯然多處理在我之前。對於任何人想知道的,我所需要的只是調用freeze_support()。 http://docs.python.org/library/multiprocessing.html#multiprocessing.freeze_support雖然它應該立即引發一個RuntimeError,所以我不確定它爲什麼會運行... – dpitch40

回答

8

在Windows上,multiprocessing嘗試通過啓動可執行文件的新實例並在其中執行其子進程例程(multiprocessing.forking.main())來模擬Unix fork()系統調用。使用標準Python解釋器(python.exe),multiprocessing可以通過-c參數運行自定義代碼。但是,對於自定義可執行文件,這是不可能的,因爲可執行文件很可能不支持與python.exe相同的命令行選項。

freeze_support()函數通過顯式地執行子進程例程來回避此問題,並通過調用sys.exit()來終止解釋器。如果您忘記調用freeze_support(),新進程不知道它是一個子進程並運行主應用程序邏輯。在你的情況下,這將彈出另一個主要的GUI窗口。

由於來自新創建的進程開始另一個子進程將導致無限遞歸,multiprocessing試圖通過檢查sys.frozen屬性,以防止這一點,並提出一個RuntimeError如果freeze_support()不叫。在你的情況下,似乎需要用戶交互來產生進程,因此沒有無限遞歸併且沒有RuntimeError

按照慣例,sys.frozen僅針對由py2exe或PyInstaller創建的自動生成的可執行文件設置。理解這個邏輯非常重要,並且當需要將Python嵌入到應該支持windows下的多處理的自定義可執行文件中時,需要將sys.frozen設置爲True

相關問題