Python 中多处理模块的池和队列问题
Issue with Pool and Queue of multiprocessing module in Python
我是 Python 的多处理新手,我写了下面的小脚本:
import multiprocessing
import os
def task(queue):
print(100)
def run(pool):
queue = multiprocessing.Queue()
for i in range(os.cpu_count()):
pool.apply_async(task, args=(queue, ))
if __name__ == '__main__':
multiprocessing.freeze_support()
pool = multiprocessing.Pool()
run(pool)
pool.close()
pool.join()
我想知道为什么不执行task()方法,运行这个脚本后没有输出。谁能帮帮我?
它是 运行,但它在主线程外因错误而死亡,因此您看不到错误。出于这个原因,.get()
异步调用的结果总是好的,即使您不关心结果:.get()
会引发否则不可见的错误。
例如,像这样更改循环:
tasks = []
for i in range(os.cpu_count()):
tasks.append(pool.apply_async(task, args=(queue,)))
for t in tasks:
t.get()
然后新的t.get()
会爆炸,结束于:
RuntimeError: Queue objects should only be shared between processes through inheritance
简而言之,不支持将 Queue
对象传递给 Pool
方法。
但是您可以将它们传递给multiprocessing.Process()
,或者Pool
初始化函数。例如,这是执行后者的一种方法:
import multiprocessing
import os
def pool_init(q):
global queue # make queue global in workers
queue = q
def task():
# can use `queue` here if you like
print(100)
def run(pool):
tasks = []
for i in range(os.cpu_count()):
tasks.append(pool.apply_async(task))
for t in tasks:
t.get()
if __name__ == '__main__':
queue = multiprocessing.Queue()
pool = multiprocessing.Pool(initializer=pool_init, initargs=(queue,))
run(pool)
pool.close()
pool.join()
在 Linux-y 系统上,您可以 - 正如原始错误消息所建议的那样 - 使用进程继承代替(但在 Windows 上这是不可能的)。
我是 Python 的多处理新手,我写了下面的小脚本:
import multiprocessing
import os
def task(queue):
print(100)
def run(pool):
queue = multiprocessing.Queue()
for i in range(os.cpu_count()):
pool.apply_async(task, args=(queue, ))
if __name__ == '__main__':
multiprocessing.freeze_support()
pool = multiprocessing.Pool()
run(pool)
pool.close()
pool.join()
我想知道为什么不执行task()方法,运行这个脚本后没有输出。谁能帮帮我?
它是 运行,但它在主线程外因错误而死亡,因此您看不到错误。出于这个原因,.get()
异步调用的结果总是好的,即使您不关心结果:.get()
会引发否则不可见的错误。
例如,像这样更改循环:
tasks = []
for i in range(os.cpu_count()):
tasks.append(pool.apply_async(task, args=(queue,)))
for t in tasks:
t.get()
然后新的t.get()
会爆炸,结束于:
RuntimeError: Queue objects should only be shared between processes through inheritance
简而言之,不支持将 Queue
对象传递给 Pool
方法。
但是您可以将它们传递给multiprocessing.Process()
,或者Pool
初始化函数。例如,这是执行后者的一种方法:
import multiprocessing
import os
def pool_init(q):
global queue # make queue global in workers
queue = q
def task():
# can use `queue` here if you like
print(100)
def run(pool):
tasks = []
for i in range(os.cpu_count()):
tasks.append(pool.apply_async(task))
for t in tasks:
t.get()
if __name__ == '__main__':
queue = multiprocessing.Queue()
pool = multiprocessing.Pool(initializer=pool_init, initargs=(queue,))
run(pool)
pool.close()
pool.join()
在 Linux-y 系统上,您可以 - 正如原始错误消息所建议的那样 - 使用进程继承代替(但在 Windows 上这是不可能的)。