我正在使用多处理对一组数据进行大量计算,以减少计算时间。除一个小的警告外,它的运行非常出色,当我的监听器进程编写输出时,输出顺序错误,这肯定是不好的。我需要所有这些都按照它进来的顺序来进行。不确定如何实现这一点。示例代码如下。
import numpy, os, multiprocessing
from multiprocessing.sharedctypes import Value, Array, RawArray, RawValue
from multiprocessing import Process, Lock
def domorestuff(value):
value += value # sample, some other calculation
q.put(value)
return
def dostuff(somevalue):
somevalue += 1 # do some calculation instead of just +=1 here
domorestuff(somevalue)
return
def listener(q):
f = open(os.path.join(outdir, fileout.value), 'w')
while 1:
#print("Listener...", flush=True)
m = q.get()
if(m == 'kill'):
break
#print("Listen write...", flush=True)
f.write(str(m) + '\n')
f.flush()
f.close()
def main():
manager = multiprocessing.Manager()
q = manager.Queue()
pool = multiprocessing.Pool(9)
watcher = pool.apply_async(listener, (q,))
pool.map(dostuff, range(8))
q.put('kill')
pool.close()
我希望它能为我提供文件中一组线性值,即:
2, 4, 6, 8, 10, 12, 14, 18
但是,它们每次都以随机顺序出现。在不同步的情况下,我不知所措,当我不使用侦听器并且不进行文件写入时,似乎按线程数按顺序加入了进程。但是很难确定,因为我不能安全地将多个线程的输出写入单个文件。
为了更清楚一点,处理过程发生在输入文件上,每个线程读取该文件所需的部分,然后将基于处理的输出写入侦听器。但是,如上所述,它不是按顺序获取块,而是以随机排序的块出现。
答案 0 :(得分:0)
您正在异步运行进程。您不能期望这些独立的流程以任何预期的顺序处理/完成他们的任务。
答案 1 :(得分:0)
@ M.Rau实际上并不正确,您可以在池中运行作业,然后将它们重新结合在一起以保留顺序,幸运的是,multiprocessing
模块可以使用pool.apply_async
来内置此功能或pool.imap
。
我稍微清理了一下代码(请注意,队列完全消失了),这就是我想到的:
import numpy, os, multiprocessing
def domorestuff(value):
return value + value # sample, some other calculation
def dostuff(somevalue):
somevalue += 1 # do some calculation instead of just +=1 here
return domorestuff(somevalue)
def main():
pool = multiprocessing.Pool(9)
out = list(pool.imap(dostuff, range(8)))
pool.close()
print (out)
有关更多信息,请查看an example from the official docs。他们在那里解释了不同的技术。顺便说一下,问题中的python代码甚至无法编译,并且侦听器功能无关紧要。希望这会有所帮助!