【发布时间】:2019-01-26 01:46:55
【问题描述】:
我正在尝试使用多处理来跨多个进程运行许多模拟;但是,据我所知,我编写的代码仅使用了 1 个进程。
更新
感谢@PaulBecotte,我已经完成了所有流程(我认为);但是,多处理似乎比其非多处理对应物的运行速度要慢得多。
例如,不包括函数和类声明/实现和导入,我有:
def monty_hall_sim(num_trial, player_type='AlwaysSwitchPlayer'):
if player_type == 'NeverSwitchPlayer':
player = NeverSwitchPlayer('Never Switch Player')
else:
player = AlwaysSwitchPlayer('Always Switch Player')
return (MontyHallGame().play_game(player) for trial in xrange(num_trial))
def do_work(in_queue, out_queue):
while True:
try:
f, args = in_queue.get()
ret = f(*args)
for result in ret:
out_queue.put(result)
except:
break
def main():
logging.getLogger().setLevel(logging.ERROR)
always_switch_input_queue = multiprocessing.Queue()
always_switch_output_queue = multiprocessing.Queue()
total_sims = 20
num_processes = 5
process_sims = total_sims/num_processes
with Timer(timer_name='Always Switch Timer'):
for i in xrange(num_processes):
always_switch_input_queue.put((monty_hall_sim, (process_sims, 'AlwaysSwitchPlayer')))
procs = [multiprocessing.Process(target=do_work, args=(always_switch_input_queue, always_switch_output_queue)) for i in range(num_processes)]
for proc in procs:
proc.start()
always_switch_res = []
while len(always_switch_res) != total_sims:
always_switch_res.append(always_switch_output_queue.get())
always_switch_success = float(always_switch_res.count(True))/float(len(always_switch_res))
print '\tLength of Always Switch Result List: {alw_sw_len}'.format(alw_sw_len=len(always_switch_res))
print '\tThe success average of switching doors was: {alw_sw_prob}'.format(alw_sw_prob=always_switch_success)
产生:
Time Elapsed: 1.32399988174 seconds
Length: 20
The success average: 0.6
但是,我试图将其用于total_sims = 10,000,000 而不是num_processes = 5,这样做所花费的时间比使用 1 个进程要长得多(1 个进程在大约 3 分钟内返回)。我与之比较的非多处理对应物是:
def main():
logging.getLogger().setLevel(logging.ERROR)
with Timer(timer_name='Always Switch Monty Hall Timer'):
always_switch_res = [MontyHallGame().play_game(AlwaysSwitchPlayer('Monty Hall')) for x in xrange(10000000)]
always_switch_success = float(always_switch_res.count(True))/float(len(always_switch_res))
print '\n\tThe success average of not switching doors was: {not_switching}' \
'\n\tThe success average of switching doors was: {switching}'.format(not_switching=never_switch_success,
switching=always_switch_success)
【问题讨论】:
-
您的子进程 - 他们从输入队列消费并导出到输出队列?您只将 4 条(现在 5 条)消息放入队列,所以这不应该是您获得的输出数量吗?
-
嗨@PaulBecotte,Python 新手,所以我可能完全搞砸了上面的代码。我正在尝试做的是创建一个包含 5 个元组 (fcn_name, (num_of_trials_to_perform,)) 的输入队列,其中函数是 Monty Hall 模拟,要执行的试验次数是要在Monty Hall 函数用于子进程。因此,总共有 20 个模拟,我想要 5 个带有 (fcn_name, (4,)) 的元组,然后在子进程中使用这些元组中的每一个。如果这有意义?
标签: python python-2.7 queue multiprocessing python-multiprocessing