Python concurrent.futures 多次调用导入的模块
Python concurrent.futures multiple calls to imported modules
在深入细节之前,我想提一下我已经阅读了这个 post,其中的问题看起来非常相似:
Spyder 4.0.1/Python3.7.1 64 位/Windows10
然而,采取了保护我的顶级代码的谨慎步骤似乎对我的情况不起作用。
我使用 concurrent.futures
和 ProcessPollExecutor
来执行下面的代码。
在 pandas 之外,numpy...代码调用两个自定义模块:HAL_PROC 和 HAL_FUNC,包含 类 和执行下面循环所需的函数。
执行时,HAL_PROC.py 调用另一个生成 GUI 的模块,她或他可以在其中指定输入路径、文件名...此值或存储在变量中。
我的问题是:当我 运行 代码时,无论是在 Spyder 中还是编译成 .exe 文件时,它都会执行 main()
函数,GUI 在屏幕上生成 8 次.即使没有调用主要部分中的模块或任何相关模块,因为所有内容都存储在变量中,甚至是函数。
我确定我遗漏了有关如何正确设置多处理代码的重要细微差别,我们将不胜感激。
import pandas as pd
import numpy as np
from HAL_PROC import N_tab, N_tab_FCT, TYPE, TR, CA
from HAL_FUNC import *
import multiprocessing
from concurrent.futures import ProcessPoolExecutor
alpha = 0.05
alg_type = TYPE
if alg_type == "O":
F = FFR_ME
elif alg_type == "NO":
F = FFR_ME_NO
else :
raise TypeError("Algortithm type selected does not exist. Must be 'O' or 'NO'")
def main():
""" Set the variables for the loop """
futures = []
e = ProcessPoolExecutor(8)
""" Loop over the different task summarized in the tab 'N_tab' during the MPO_PROC step. """
for task in N_tab["TASK_NUMBER"]:
""" Declare variables N, n , f based on the previous calculations """
N = int(N_tab.loc[N_tab["TASK_NUMBER"] == task, "N_Task"])
n = int(N_tab.loc[N_tab["TASK_NUMBER"] == task, "n_i"])
f = int(N_tab.loc[N_tab["TASK_NUMBER"] == task, "F"])
"""" Implement the function using the concurrent.future module for multiprocessing. """
future = e.submit(F, N, n, f, alpha)
futures.append(future)
results = [ff.result() for ff in futures]
for i in range(len(results)):
f = int(N_tab.loc[i, "F"])
N_tab.loc[i,"LBound"] = results[i][0][f]
N_tab.loc[i,"UBound"] = results[i][1][f]
N_tab.loc[i,"ME"] = (N_tab.loc[i,"UBound"] - N_tab.loc[i,"LBound"])/\
(2*N_tab.loc[i,"N_Task"])
N_tab.loc[i,"FFR"] = (N_tab.loc[i,"LBound"] + (N_tab.loc[i,"UBound"] - N_tab.loc[i,"LBound"])/2)/\
N_tab.loc[i,"N_Task"]
if __name__ == "__main__":
multiprocessing.freeze_support()
main()
经过一番挖掘,我找到了解决问题的方法,以防万一。
与我发现的很多帖子相反,用 if "__name__" == __main__
保护我的代码是不够的。
1) 我更改为 multiprocessing
库而不是 concurrent.future
,这是前者的简化版本。 (见下面的代码)。
2) 结果表明,在 Ipython 控制台中 Windows 的多处理不是很可靠 ()。解决多次调用import
的问题
我在开头添加了这段代码:
import sys
sys.modules['__main__'].__file__ = 'ipython'
最后,代码看起来像这样并且工作完美,(不再有损坏的进程池或弹出多个 GUI)。
import pandas as pd
import numpy as np
import json
from HAL_PROC import N_tab, N_tab_FCT, TYPE, TR, CA
from HAL_FUNC import *
from HAL_GRAPH import Dossier_graph, Forecast_graph
from multiprocessing import Pool
import multiprocessing as mp
import matplotlib.backends.backend_pdf
import sys
sys.modules['__main__'].__file__ = 'ipython'
""" ========================================================== """
""" FFR +/- ME CALCULATION """
""" ========================================================== """
def main():
with Pool() as p:
results = p.starmap(F,zip(N,n,f,alpha))
results_fct = p.starmap(F,zip(N_fct,n_fct,f_fct,alpha_fct))
p.close()
p.join()
if __name__ == "__main__":
N_tab, N_tab_FCT = main()
在深入细节之前,我想提一下我已经阅读了这个 post,其中的问题看起来非常相似:
Spyder 4.0.1/Python3.7.1 64 位/Windows10
然而,采取了保护我的顶级代码的谨慎步骤似乎对我的情况不起作用。
我使用 concurrent.futures
和 ProcessPollExecutor
来执行下面的代码。
在 pandas 之外,numpy...代码调用两个自定义模块:HAL_PROC 和 HAL_FUNC,包含 类 和执行下面循环所需的函数。
执行时,HAL_PROC.py 调用另一个生成 GUI 的模块,她或他可以在其中指定输入路径、文件名...此值或存储在变量中。
我的问题是:当我 运行 代码时,无论是在 Spyder 中还是编译成 .exe 文件时,它都会执行 main()
函数,GUI 在屏幕上生成 8 次.即使没有调用主要部分中的模块或任何相关模块,因为所有内容都存储在变量中,甚至是函数。
我确定我遗漏了有关如何正确设置多处理代码的重要细微差别,我们将不胜感激。
import pandas as pd
import numpy as np
from HAL_PROC import N_tab, N_tab_FCT, TYPE, TR, CA
from HAL_FUNC import *
import multiprocessing
from concurrent.futures import ProcessPoolExecutor
alpha = 0.05
alg_type = TYPE
if alg_type == "O":
F = FFR_ME
elif alg_type == "NO":
F = FFR_ME_NO
else :
raise TypeError("Algortithm type selected does not exist. Must be 'O' or 'NO'")
def main():
""" Set the variables for the loop """
futures = []
e = ProcessPoolExecutor(8)
""" Loop over the different task summarized in the tab 'N_tab' during the MPO_PROC step. """
for task in N_tab["TASK_NUMBER"]:
""" Declare variables N, n , f based on the previous calculations """
N = int(N_tab.loc[N_tab["TASK_NUMBER"] == task, "N_Task"])
n = int(N_tab.loc[N_tab["TASK_NUMBER"] == task, "n_i"])
f = int(N_tab.loc[N_tab["TASK_NUMBER"] == task, "F"])
"""" Implement the function using the concurrent.future module for multiprocessing. """
future = e.submit(F, N, n, f, alpha)
futures.append(future)
results = [ff.result() for ff in futures]
for i in range(len(results)):
f = int(N_tab.loc[i, "F"])
N_tab.loc[i,"LBound"] = results[i][0][f]
N_tab.loc[i,"UBound"] = results[i][1][f]
N_tab.loc[i,"ME"] = (N_tab.loc[i,"UBound"] - N_tab.loc[i,"LBound"])/\
(2*N_tab.loc[i,"N_Task"])
N_tab.loc[i,"FFR"] = (N_tab.loc[i,"LBound"] + (N_tab.loc[i,"UBound"] - N_tab.loc[i,"LBound"])/2)/\
N_tab.loc[i,"N_Task"]
if __name__ == "__main__":
multiprocessing.freeze_support()
main()
经过一番挖掘,我找到了解决问题的方法,以防万一。
与我发现的很多帖子相反,用 if "__name__" == __main__
保护我的代码是不够的。
1) 我更改为 multiprocessing
库而不是 concurrent.future
,这是前者的简化版本。 (见下面的代码)。
2) 结果表明,在 Ipython 控制台中 Windows 的多处理不是很可靠 (import
的问题
我在开头添加了这段代码:
import sys
sys.modules['__main__'].__file__ = 'ipython'
最后,代码看起来像这样并且工作完美,(不再有损坏的进程池或弹出多个 GUI)。
import pandas as pd
import numpy as np
import json
from HAL_PROC import N_tab, N_tab_FCT, TYPE, TR, CA
from HAL_FUNC import *
from HAL_GRAPH import Dossier_graph, Forecast_graph
from multiprocessing import Pool
import multiprocessing as mp
import matplotlib.backends.backend_pdf
import sys
sys.modules['__main__'].__file__ = 'ipython'
""" ========================================================== """
""" FFR +/- ME CALCULATION """
""" ========================================================== """
def main():
with Pool() as p:
results = p.starmap(F,zip(N,n,f,alpha))
results_fct = p.starmap(F,zip(N_fct,n_fct,f_fct,alpha_fct))
p.close()
p.join()
if __name__ == "__main__":
N_tab, N_tab_FCT = main()