2017-07-04 77 views
0

嗨,我試圖用多,以加快我的代碼。但是,apply_async不適用於我。我試圖做一個簡單的例子,如:的Python - apply_async不執行功能

from multiprocessing.pool import Pool 
t = [0, 1, 2, 3, 4, 5] 
def cube(x): 
    t[x] = x**3 
pool = Pool(processes=4) 
for i in range(6): 
    pool.apply_async(cube, args=(i,)) 
for x in t: 
    print(x) 

它並沒有真正改變t如我所料。

我真正的代碼如下:

from multiprocessing.pool import Pool 
def func(a, b, c, d): 
    #some calculations 
    #save result to files 
    #no return value 
lt = #list of possible value of a 
#set values to b, c, d 
p = Pool() 
for i in lt: 
    p.apply_async(func, args=(i, b, c, d,)) 

哪裏是這裏的問題?

謝謝!


更新:感謝評論和答案,現在我明白了爲什麼我的簡單示例不起作用。但是,我仍然遇到了我的真實代碼問題。我已經檢查過我的func不依賴任何全局變量,所以它看起來不像我的示例代碼那樣。

至於建議,我添加了一個返回值,我func,現在我的代碼是:

f = Flux("reactor") 
d = Detector("Ge") 
mv = arange(-6, 1.5, 0.5) 
p = Pool() 
lt = ["uee", "dee"] 
for i in lt: 
    re = p.apply_async(res, args=(i, d, f, mv,)) 
    print(re.get()) 
p.close() 
p.join() 

現在我得到以下錯誤:

Traceback (most recent call last): 
    File "/Users/Shu/Documents/Programming/Python/Research/debug.py", line 35, in <module> 
print(re.get()) 
    File "/usr/local/Cellar/python3/3.6.0/Frameworks/Python.framework/Versions/3.6/lib/python3.6/multiprocessing/pool.py", line 608, in get 
raise self._value 
    File "/usr/local/Cellar/python3/3.6.0/Frameworks/Python.framework/Versions/3.6/lib/python3.6/multiprocessing/pool.py", line 385, in _handle_tasks 
put(task) 
    File "/usr/local/Cellar/python3/3.6.0/Frameworks/Python.framework/Versions/3.6/lib/python3.6/multiprocessing/connection.py", line 206, in send 
self._send_bytes(_ForkingPickler.dumps(obj)) 
    File "/usr/local/Cellar/python3/3.6.0/Frameworks/Python.framework/Versions/3.6/lib/python3.6/multiprocessing/reduction.py", line 51, in dumps 
cls(buf, protocol).dump(obj) 
AttributeError: Can't pickle local object 'Flux.__init__.<locals>.<lambda>' 
+0

是'FUNC()'不創建文件不如預期,或者你只是沒有看到任何速度優勢? –

+0

@JohnGordon'func'不會做任何事情,就像我的第一個例子'cube'沒有執行。 –

+0

您假定每個進程共享相同的全局't',這是從定義上來說是不可信的。您必須將't'作爲參數傳遞,以便't'存在並且被所有進程共享。 –

回答

0

編輯:你提供的第一個例子不起作用出於一個簡單的原因:進程不共享內存。因此,更改t[x] = x**3將不會應用於父進程,使列表t的值保持不變。

你需要真正從計算返回值,並從建立一個新的列表。

def cube(x): 
    return x**3 

t = [0, 1, 2, 3, 4, 5] 

p = Pool() 
t = p.map(cube, t) 

print(t) 

如果你在第二個例子中要求,結果應該不會,但可獨立保存的文件中返回,並不會發生這種情況,我建議你檢查你函數的返回值以查看函數本身是否引發異常。

我建議你得到的實際效果,看看會發生什麼:

p = Pool() 
for i in lt: 
    res = p.apply_async(func, args=(i, b, c, d,)) 
    print(res.get()) # this will raise an exception if it happens within func 

p.close() # do not accept any more tasks 
p.join() # wait for the completion of all scheduled jobs 
+0

這對我無效.. –

+0

編輯答案。 – noxdafox

+0

感謝您的耐心等待!現在我收到了一個錯誤,請參閱我的更新問題。 –

-1

功能過早地退出,請嘗試添加在你的劇本結束這段代碼:

import time 
time.sleep(3)