收集python中不同进程的结果

时间:2013-07-29 14:50:58

标签: python parallel-processing

我正在做几个过程。每个进程都返回一些结果。我如何从这些过程中收集这些结果。

 task_1 = Process(target=do_this_task,args=(para_1,para_2))
 task_2 = Process(target=do_this_task,args=(para_1,para_2))

do_this_task会返回一些结果。我想收集这些结果并将它们保存在一些变量中。

3 个答案:

答案 0 :(得分:1)

所以现在我建议你应该使用python multiprocessing模块的Pool,因为它可以为你处理很多。你能详细说明你在做什么以及为什么要直接使用我认为是multiprocessing.Process的东西吗?

如果您仍想直接使用multiprocessing.Process,则应使用队列来获取返回值。

文档中给出的示例:

from multiprocessing import Process, Queue

def f(q):
    q.put([42, None, 'hello'])

if __name__ == '__main__':
    q = Queue()
    p = Process(target=f, args=(q,))
    p.start()
    print q.get()    # prints "[42, None, 'hello']"
    p.join()

“ - Multiprocessing Docs

因此,流程通常在后台运行以执行某些操作,如果您使用它们进行多处理,则需要“抛弃”数据,因为进程没有像线程一样的共享内存 - 这就是您使用的原因队列 - 它为你做到了。你可以做的另一件事是管道,方便的是他们也给出了一个例子:)。 “

from multiprocessing import Process, Pipe

def f(conn):
    conn.send([42, None, 'hello'])
    conn.close()

if __name__ == '__main__':
    parent_conn, child_conn = Pipe()
    p = Process(target=f, args=(child_conn,))
    p.start()
    print parent_conn.recv()   # prints "[42, None, 'hello']"
    p.join()

” - Multiprocessing Docs

这样做是在这种情况下手动使用管道将完成的结果抛到'父进程'。

有时我也会发现multiprocessing无法发现的情况,所以我使用mrule from multiprocessing import Process, Pipe from itertools import izip def spawn(f): def fun(pipe,x): pipe.send(f(x)) pipe.close() return fun def parmap(f,X): pipe=[Pipe() for x in X] proc=[Process(target=spawn(f),args=(c,x)) for x,(p,c) in izip(X,pipe)] [p.start() for p in proc] [p.join() for p in proc] return [p.recv() for (p,c) in pipe] if __name__ == '__main__': print parmap(lambda x:x**x,range(1,5)) 发布的ls这个很棒的答案(或我修改后的专业变体):

subprocess

然而,应该警告你,这会手动控制过程的控制,所以某些东西可能会留下“死”的过程 - 这不是一件好事,一个例子是意外的信号 - 这是一个使用管道的例子多处理虽然:)。

如果这些命令不在python中,例如你想运行os.system,那么使用subprocess可能会更好,因为{{1}}不再是一件好事,因为它现在被认为是{{1}}是一个更易于使用且更灵活的工具,提供了一个讨论here

答案 1 :(得分:1)

您可以使用multiprocessing

做类似的事情
from multiprocessing import Pool

mydict = {}
with Pool(processes=5) as pool:
        task_1 = pool.apply_async(do_this_task,args=(para_1,para_2))
        task_2 = pool.apply_async(do_this_task,args=(para_1,para_2))
        mydict.update({"task_1": task_1.get(), "task_2":task_2.get()})
print(mydict)

或者,如果您想尝试使用concurrent.futures进行多线程处理,请查看此answer

答案 2 :(得分:0)

如果进程是外部脚本,请尝试使用subprocess模块。但是,您的代码建议您要并行运行函数。为此,请尝试multiprocessing模块。来自this的一些代码回答了有关使用多处理的具体细节:

def foo(bar, baz):
    print 'hello {0}'.format(bar)
    return 'foo' + baz

from multiprocessing.pool import ThreadPool
pool = ThreadPool(processes=1)

async_result = pool.apply_async(foo, ('world', 'foo')) # tuple of args for foo

# do some other stuff in the other processes

return_val = async_result.get()  # get the return value from your function.