2013-12-20 27 views
3

我想知道啓動一個工作池來並行管理一個任務或啓動單個進程來執行酸洗和分配作業之間有什麼區別。Python多處理,進程和池之間的區別,數據的酸洗

我有一個任務(這裏是do_my_job)的對象不能被酸洗。因此,我無法啓動一批工人並行執行任務。下面的代碼片段無法正常工作,在那裏iterator遍歷不同的參數設置do_my_job

import multiprocessing as multip 

mpool = multip.Pool(ncores) 
mpool.map(do_my_job, iterator) 
mpool.close() 
mpool.join() 

然而,下面的代碼片段沒有工作:

import time 
import multiprocessing as multip 

keep_running=True 
process_list = [] 

while len(process_list)>0 or keep_running: 

    terminated_procs = [] 
    for idx, proc in enumerate(process_list): 

     if not proc.is_alive(): 
      terminated_procs.append(idx) 

    for terminated_proc in terminated_procs: 
     process_list.pop(terminated_proc) 

    if len(process_list) < ncores and keep_running: 
     try: 
      task = iterator.next() 
      proc = multip.Process(target=do_my_job, 
                args=(task,)) 

      proc.start() 
      process_list.append(proc) 
     except StopIteration: 
      keep_running=False 


    time.sleep(0.1) 

如何我在後一種情況下的工作分配給個別進程?在流程開始之前是否沒有酸洗任務和涉及所有相關對象的步驟?如果不是如何將任務和對象傳遞給新進程?

回答

4

當你fork一個新的進程的子進程將繼承他的父母的數據。因此,如果父母在分叉之前定義變量,則孩子將能夠看到它,因爲它是它自己的變量。在系統調用子進程和父進程之後,應該使用某個IPC在它們之間共享數據。 當您創建一個Pool時,您分叉了N個進程,然後當您撥打map時,您會將它們傳遞給他們。但是,因爲這些過程已經分叉了,所以共享這些數據的唯一方法就是使用包含「酸洗」對象的IPC。在後一種情況下,您在之後創建,因此子進程能夠訪問它,因爲它在自己的位置。 我認爲你可以做的最好的事情就是讓你的對象「可選」。

+0

複製了繼承的數據,對吧?因此,無論子進程對數據做什麼都不會修改父類的數據?! 不幸的是,我不能讓我的對象「可選」,因爲它的一部分來自第三方應用程序。 – SmCaterpillar

+1

通常它是「寫入時複製」。孩子和父母會分享相同的「記憶」,直到他們中的一人嘗試寫作,然後複製。 – smeso

+0

@SmCaterpillar,您的主程序如何訪問這些第三方對象?您可以在您的Pool進程中使用相同類型的代碼來訪問它們,可能是在進程初始化函數中。這裏沒有足夠的細節來充實它。在極端情況下,您可以將代碼作爲*字符串*和'exec'傳遞給Pool進程中的字符串。總是有替代品;-) –