在多处理期间保持统一计数?
Keep unified count during multiprocessing?
我有一个 python 程序,它 运行 是一个 Monte Carlo 模拟来寻找概率问题的答案。我正在使用多处理,这里是伪代码
import multiprocessing
def runmycode(result_queue):
print "Requested..."
while 1==1:
iterations +=1
if "result found (for example)":
result_queue.put("result!")
print "Done"
processs = []
result_queue = multiprocessing.Queue()
for n in range(4): # start 4 processes
process = multiprocessing.Process(target=runmycode, args=[result_queue])
process.start()
processs.append(process)
print "Waiting for result..."
result = result_queue.get() # wait
for process in processs: # then kill them all off
process.terminate()
print "Got result:", result
我想扩展它,以便我可以统一计算 运行 的迭代次数。就像如果线程 1 有 运行 100 次而线程 2 有 运行 100 次那么我想显示总共 200 次迭代,作为控制台的打印。我指的是线程进程中的 iterations
变量。我怎样才能确保所有线程都添加到同一个变量?我认为使用 iterations
的 Global
版本会起作用,但它不起作用。
普通全局变量在进程之间的共享方式与在线程之间共享的方式不同。您需要使用 process-aware 数据结构。对于您的 use-case,multiprocessing.Value
应该可以正常工作:
import multiprocessing
def runmycode(result_queue, iterations):
print("Requested...")
while 1==1: # This is an infinite loop, so I assume you want something else here
with iterations.get_lock(): # Need a lock because incrementing isn't atomic
iterations.value += 1
if "result found (for example)":
result_queue.put("result!")
print("Done")
if __name__ == "__main__":
processs = []
result_queue = multiprocessing.Queue()
iterations = multiprocessing.Value('i', 0)
for n in range(4): # start 4 processes
process = multiprocessing.Process(target=runmycode, args=(result_queue, iterations))
process.start()
processs.append(process)
print("Waiting for result...")
result = result_queue.get() # wait
for process in processs: # then kill them all off
process.terminate()
print("Got result: {}".format(result))
print("Total iterations {}".format(iterations.value))
一些注意事项:
- 我明确地将
Value
传递给了 children,以保持代码与 Windows 兼容,这不能在 [=34] 之间共享 read/write 全局变量=] 和 children.
- 我用锁保护增量,因为它不是原子操作,并且容易出现竞争条件。
- 我添加了一个
if __name__ == "__main__":
守卫,再次帮助 Windows 兼容性,作为一般最佳实践。
我有一个 python 程序,它 运行 是一个 Monte Carlo 模拟来寻找概率问题的答案。我正在使用多处理,这里是伪代码
import multiprocessing
def runmycode(result_queue):
print "Requested..."
while 1==1:
iterations +=1
if "result found (for example)":
result_queue.put("result!")
print "Done"
processs = []
result_queue = multiprocessing.Queue()
for n in range(4): # start 4 processes
process = multiprocessing.Process(target=runmycode, args=[result_queue])
process.start()
processs.append(process)
print "Waiting for result..."
result = result_queue.get() # wait
for process in processs: # then kill them all off
process.terminate()
print "Got result:", result
我想扩展它,以便我可以统一计算 运行 的迭代次数。就像如果线程 1 有 运行 100 次而线程 2 有 运行 100 次那么我想显示总共 200 次迭代,作为控制台的打印。我指的是线程进程中的 iterations
变量。我怎样才能确保所有线程都添加到同一个变量?我认为使用 iterations
的 Global
版本会起作用,但它不起作用。
普通全局变量在进程之间的共享方式与在线程之间共享的方式不同。您需要使用 process-aware 数据结构。对于您的 use-case,multiprocessing.Value
应该可以正常工作:
import multiprocessing
def runmycode(result_queue, iterations):
print("Requested...")
while 1==1: # This is an infinite loop, so I assume you want something else here
with iterations.get_lock(): # Need a lock because incrementing isn't atomic
iterations.value += 1
if "result found (for example)":
result_queue.put("result!")
print("Done")
if __name__ == "__main__":
processs = []
result_queue = multiprocessing.Queue()
iterations = multiprocessing.Value('i', 0)
for n in range(4): # start 4 processes
process = multiprocessing.Process(target=runmycode, args=(result_queue, iterations))
process.start()
processs.append(process)
print("Waiting for result...")
result = result_queue.get() # wait
for process in processs: # then kill them all off
process.terminate()
print("Got result: {}".format(result))
print("Total iterations {}".format(iterations.value))
一些注意事项:
- 我明确地将
Value
传递给了 children,以保持代码与 Windows 兼容,这不能在 [=34] 之间共享 read/write 全局变量=] 和 children. - 我用锁保护增量,因为它不是原子操作,并且容易出现竞争条件。
- 我添加了一个
if __name__ == "__main__":
守卫,再次帮助 Windows 兼容性,作为一般最佳实践。