odeint関数を使用して常微分方程式系を解いています。この種の問題を簡単に並列化することは可能ですか?
3 に答える
上記の答えは間違っています。ODE を数値的に解くには、反復ごとに関数 f(t,y)=y' を数回計算する必要があります。たとえば、ルンゲクッタの場合は 4 回です。しかし、これを行うpythonのパッケージは知りません。
ODE の数値積分は、次の結果を計算するために各結果が必要になるため、本質的に逐次的な操作です (ただし、複数の開始点から積分する場合を除きます)。だから答えはノーだと思います。
編集:うわー、この質問が3年以上前のものだと気づきました。同じ苦境にある誰かに道が見つかることを願って、私はまだ答えを残します. そのために残念。
私も同じ問題を抱えていました。このようなプロセスを次のように並列化できました。
最初にdispyが必要です。そこには、並列化プロセスを実行するプログラムがいくつかあります。私は専門家ではありませんdispy
が、問題なく使用でき、何も設定する必要もありませんでした。
それで、それをどのように使用するのですか?
実行します
python dispynode.py -d
。メイン プログラムを実行する前にこのスクリプトを実行しないと、並列ジョブは実行されません。メイン プログラムを実行します。ここに私が使用したものを投稿します(混乱して申し訳ありません)。function を変更し、
sim
それに応じて結果をどうしたいかを変更する必要があります。ただし、私のプログラムが参考になることを願っています。import os, sys, inspect #Add dispy to your path cmd_folder = os.path.realpath(os.path.abspath(os.path.split(inspect.getfile( inspect.currentframe() ))[0])) if cmd_folder not in sys.path: sys.path.insert(0, cmd_folder) # use this if you want to include modules from a subforder cmd_subfolder = os.path.realpath(os.path.abspath(os.path.join(os.path.split(inspect.getfile( inspect.currentframe() ))[0],cmd_folder+"/dispy-3.10/"))) if cmd_subfolder not in sys.path: sys.path.insert(0, cmd_subfolder) #----------------------------------------# #This function contains the differential equation to be simulated. def sim(ic,e,O): #ic=initial conditions; e=Epsiolon; O=Omega from scipy.integrate import ode import numpy as np #Diff Eq. def sys(t,x,e,O,z,b,l): p = 2.*e*O*np.sin(O*t)*(1-e*np.cos(O*t))/(z+(1-e*np.cos(O*t))**2) q = (1+4.*b/l*np.cos(O*t))*(z+(1-e*np.cos(O*t)))/( z+(1-e*np.cos(O*t))**2 ) dx=np.zeros(2) dx[0] = x[1] dx[1] = -q*x[0]-p*x[1] return dx #Simulation. t0=0; tEnd=10000.; dt=0.1 r = ode(sys).set_integrator('dop853', nsteps=10,max_step=dt) #Definition of the integrator Y=[];S=[];T=[] # - parameters - # z=0.5; l=1.0; b=0.06; # -------------- # color=1 r.set_initial_value(ic, t0).set_f_params(e,O,z,b,l) #Set the parameters, the initial condition and the initial time #Loop to integrate. while r.successful() and r.t +dt < tEnd: r.integrate(r.t+dt) Y.append(r.y) T.append(r.t) if r.y[0]>1.25*ic[0]: #Bound. This is due to my own requirements. color=0 break #r.y contains the solutions and r.t contains the time vector. return e,O,color #For each pair e,O return e,O and a color (0,1) which correspond to the color of the point in the stability chart (0=unstable) (1=stable) # ------------------------------------ # #MAIN PROGRAM where the parallel magic happens import matplotlib.pyplot as plt import dispy import numpy as np F=100 #Total files #Range of the values of Epsilon and Omega Epsilon = np.linspace(0,1,100) Omega_intervals = np.linspace(0,4,F) ic=[0.1,0] cluster = dispy.JobCluster(sim) #This function sets that the cluster (array of processors) will be assigned the job sim. jobs = [] #Initialize the array of jobs for i in range(F-1): Data_Array=[] jobs = [] Omega=np.linspace(Omega_intervals[i], Omega_intervals[i+1],10) print Omega for e in Epsilon: for O in Omega: job = cluster.submit(ic,e,O) #Send to the cluster a job with the specified parameters jobs.append(job) #Join all the jobs specified above cluster.wait() #Do the jobs for job in jobs: e,O,color = job() Data_Array.append([e,O,color]) #Save the results of the simulation. file_name='Data'+str(i)+'.txt' f=open(file_name, 'a') f.write(str(Data_Array)) f.close()