Python 2.7 に基づく数学ソフトウェア SageMath を使用しています。次の単純化されたコードは、最初の見積もりから始まる 2 つの関数を再帰的に計算するものです。組み込み関数を使用する代わりに、「数値積分演算子」をコードに導入しようとすると、エラーが発生します。
> PicklingError: Can't pickle <type 'function'>: attribute lookup __ builtin__.function failed
コードは次のとおりです。
reset()
forget()
from multiprocessing import Pool, cpu_count
#variables
var('x,y, x1,y1')
N=5 #number of iterations
var('q')
#functions' name definition (without specifying the rules) # n is the level of estimation
U0=[]
U1=[]
for n in range(N+1):
U0.append(function('U0_%s' %i, x,y))
U1.append(function('U1_%s' %i, x,y, x1,y1))
#initial estimation of the functions
U0[0]=sin(x+y)
U1[0]=sin(x1+y1)*cos(x-y)
#numerical integrator
num=20.0 # at each call of the int function h is assigned (b-a)/num, so assigned to num here
def numint(f, x, a, b, h):
#pickle_function(f)
integ = 0.5*h*(f(x=a) + f(x=b))
for i in range(1,num):
integ = integ + h * f(x=a+i*h)
return integ
#the integral operators
def Ix(f,x):
return pool.apply( numint, (f,x,-1.0,+1.0,2.0/num) )
def Iy(f,y):
return pool.apply_async( numint, (f,y,-1.0,+1.0,2.0/num) )
def IR(f,x,y):
return Iy(Ix(f,x),y)
def N0(n,f0,f1):
return f0[n] + IR(f1[n],x1,y1) + IR(IR(f1[n],x,y),x1,y1)
def N1(n,f0,f1):
return f1[n] + IR(f0[n],x,y) - IR(IR(f1[n],x,y),x1,y1)
#the calculations
pool = Pool(processes=cpu_count())
for n in range(N):
worker0 = N0(n,U0,U1)
worker1 = N1(n,U0,U1)
U0[n+1] = U0[n] - worker0.get()
U1[n+1] = U1[n] - worker1.get()
show(U0[n+1])
show(U1[n+1])
Web を検索してドキュメントを読んで理解した限りでは、このピッキング エラーは、整数演算子 (とにかく関数) がピッキング可能でないか、その引数がピクル可能でないためです。演算子自体を pickle 化できるように試みましたが成功しませんでしたが、問題は積分演算子自体が被積分関数の汎関数であることにあると思います。非常に最初なので、オペレーターの最初の引数 (それ自体が関数) がトップレベルで明確に定義されていないことが、オペレーターが全体的にピクル可能ではない理由でしょうか? このエラーを克服する方法はありますか?
注. メイン コードは、ここで提供する最小限のコードよりもはるかに複雑であるため、コードが読みにくくなるように整数演算子を定義する必要があります。