Python multiprocessing模块pool.join()执行不结束问题如何解决?
可能的诱因
apply_async参数传递错误:pool.apply_async的args参数要求传入可迭代的元组,你直接传args=df会触发DataFrame的迭代逻辑,将每一列作为单独参数传给find_pattern函数,而该函数只接收1个位置参数,子进程会直接抛出参数不匹配的异常,且默认不会将异常抛回主进程,导致主进程无限等待子进程返回。- Windows平台spawn模式的输入阻塞:你的
pattern = input(...)代码定义在全局作用域,Windows系统下Python多进程默认使用spawn启动模式,子进程启动时会重新导入主模块,触发顶层input()执行,子进程会阻塞等待用户输入,导致主进程join时无限等待。 - 全局变量跨进程共享异常:你直接在子进程函数
find_pattern中使用全局变量pattern,部分场景下全局变量在进程间序列化传递失败会导致子进程崩溃无返回。
排查解决方法
- 首先修正参数传递写法,将
args=df改为args=(df,),加逗号生成单元素元组,保证DataFrame作为唯一参数传入目标函数:
pool.apply_async(find_pattern, args=(df,), callback=collect_result)
- 将全局作用域的
input和pattern定义移入if __name__ == '__main__'代码块内,同时将pattern作为参数传入子进程函数,避免子进程重复执行输入逻辑:
def find_pattern(data, pattern): data['count'] = data['sequence'].str.count(pattern) occs = data[data['count'] > 0].sort_values('count', ascending=False) return occs['count'].values[:10] if __name__ == '__main__': pattern = input('Input the pattern to be searched: ') pattern = pattern.upper() pool = mp.Pool(mp.cpu_count()) results = [] for k in [(j*100)+1 for j in range(10)]: df = pd.read_csv('data.csv', skiprows=k, nrows=100, header=None) df = df.rename(columns={0:'structureId', 1:'sequence'}) # 把pattern也传入参数 pool.apply_async(find_pattern, args=(df, pattern), callback=collect_result)
- 给
apply_async添加异常回调,打印子进程的报错信息,快速定位问题:
def err_call_back(e): print(f"子进程报错:{e}") pool.apply_async(find_pattern, args=(df, pattern), callback=collect_result, error_callback=err_call_back)
- 若仍有问题,可先将进程池大小改为
processes=1测试单进程池下逻辑是否正常,再逐步扩容排查进程间通信问题。
内容的提问来源于stack exchange,提问作者Python_begginer23
相关产品推荐
相关产品推荐

