[英]Python run function parallel
我想运行一个“主要”功能n次。 该功能在运行时会启动其他功能。 “主要”功能称为“重复”,运行时首先启动功能“ copula_sim”,然后从那里获得名为“ total_summe_liste”的输出。 该列表将被添加到“ mega_summe_list”中,以确保n次运行的所有输出的安全。 排序后的“ total_summe_liste”将安全地存储为“ RM_list”,这是函数“ VaR_func”,“ CVaR_func”和“ power_func”的输入,它们均会生成输出,并按特定列表“ RM_VaR_list”,“ RM_CVaR_list”或“ RM_PSRM_list”。 之后,将清除“ RM_list”和“ total_summe_liste”,然后开始下一次运行。
最后,我得到了“ mega_summe_list”,“ RM_VaR_list”,“ RM_CVaR_list”和“ RM_PSRM_list”,它们将用于生成图形和数据框。
现在,我要并行运行“重复”功能。 例如,当我要运行此函数n = 10次时,我想同时在10个CPU内核上运行它。 原因是“ copula_sim”是一个蒙特卡罗模拟,当我进行大型模拟时会花费一些时间。
我所拥有的是:
total_summe_liste = []
RM_VaR_list = []
RM_CVaR_list = []
RM_PSRM_list = []
mega_summe_list = []
def repeat():
global RM_list
global total_summe_liste
global RM_VaR_list
global RM_CVaR_list
global RM_PSRM_list
global mega_summe_list
copula_sim(runs_sim, rand_x, rand_y, mu, full_log=False)
mega_summe_list += total_summe_liste
RM_list = sorted(total_summe_liste)
VaR_func(alpha)
RM_VaR_list.append(VaR)
CVaR_func(alpha)
RM_CVaR_list.append(CVaR)
power_func(gamma)
RM_PSRM_list.append(risk)
RM_list = []
total_summe_liste = []
n = 10
for i in range(0,n):
repeat()
到目前为止,它一直在工作。
我尝试过:
if __name__ == '__main__':
jobs = []
for i in range(0,10):
p = mp.Process(target=repeat)
jobs.append(p)
p.start()
但是,当我运行此命令时,“ mega_summe_list”为空。当我添加“ print(VaR)重复一次时,它会显示完成后的所有10 VaR。因此,并行任务到目前为止已经可以正常工作了。
问题是什么?
出现此问题的原因是,列表mega_summe_list
在进程之间不共享。
当您在python中调用并行处理时,所有函数和变量都将导入并在不同进程中独立运行。
因此,例如,当您启动5个进程时,这些变量的5个不同副本将被导入并独立运行。 因此,当您在main中访问mega_summe_list
,它仍然为空,因为在此过程中它为空。
要启用进程之间的同步,可以使用多处理程序包中的列表代理。 多处理管理器维护一个独立的服务器进程,这些Python对象存放在该服务器进程中。
以下是用于创建多处理管理器列表的代码,
from multiprocessing import Manager
mega_summe_list = Manager().List()
使用多处理时,可以使用以上代码代替mega_summe_list = []
。
下面是一个例子
from multiprocessing.pool import Pool
from multiprocessing import Manager
def repeat_test(_):
global b, mp_list
a = [1,2,3]
b += a
mp_list += a # Multiprocessing Manager List
a = []
if __name__ == "__main__":
b = []
mp_list = Manager().list()
p = Pool(5)
p.map(repeat_test, range(5))
print("a: {0}, \n mp_list: {1}".format(b, mp_list))
输出:
b: [],
mp_list: [1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3]
希望这能解决您的问题。
您应该使用Multiprocessing Pool ,然后可以执行以下操作:
p = Pool(10)
p.map(repeat, range(10))
我这样解决了这个问题:
此函数是我想以并行方式重复n次的函数:
from multiprocessing import Process
from multiprocessing import Manager
from multiprocessing.pool import Pool
def repeat(shared_list, VaR_list, CVaR_list, PSRM_list, i):
global RM_list
global total_summe_liste
copula_sim(runs_sim, rand_x, rand_y, mu, full_log=False)
shared_list += total_summe_liste
RM_list = sorted(total_summe_liste)
VaR_func(alpha)
VaR_list.append(VaR)
CVaR_func(alpha)
CVaR_list.append(CVaR)
power_func(gamma)
PSRM_list.append(risk)
RM_list = []
total_summe_liste = []
这部分管理共享列表并执行并行处理。 谢谢@ noufel13!
RM_VaR_list = []
RM_CVaR_list = []
RM_PSRM_list = []
mega_summe_list = []
if __name__ == "__main__":
with Manager() as manager:
shared_list = manager.list()
VaR_list = manager.list()
CVaR_list = manager.list()
PSRM_list = manager.list()
processes = []
for i in range(12):
p = Process(target=repeat, args=(shared_list, VaR_list, CVaR_list, PSRM_list, i)) # Passing the list
p.start()
processes.append(p)
for p in processes:
p.join()
RM_VaR_list += VaR_list
RM_CVaR_list += CVaR_list
RM_PSRM_list += PSRM_list
mega_summe_list += shared_list
RM_frame_func()
plotty_func()
谢谢!
剩下的唯一问题是我如何处理大数组? 有没有办法有效地做到这一点? 12个共享列表之一可以包含超过100.000.000个项目,因此mega_summe_list总共具有约1.200.000.000个项目...
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.