定义一些函数运算符时的PicklingError

时间:2013-02-12 20:58:04

标签: python python-2.7 multiprocessing pickle

我正在使用基于Python 2.7的数学软件SageMath。以下简化代码是从初始估计开始递归计算两个函数。当我尝试在代码中引入“数值积分运算符”时,它不会使用内置函数,而是会出错:

> 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])

据我所知,从搜索网页和阅读文档时,这种酸洗错误要么是因为整数运算符(无论如何都是函数)不是Picklable,要么是因为它的参数不可选。我试图让运算符本身可选,但没有成功,但我想问题应该是由于积分运算符本身是其被积函数的函数,并且因为它是一个运算符它的被积函数从一开始就没有确定,所以运营商的第一个参数(它本身就是一个函数)可能没有在顶层明确定义,这是运营商不能整体选择的原因吗?知道如何克服这个错误吗?

注意即可。主代码比这里提供的简约代码复杂得多,所以我宁愿定义一个整数运算符来阻止代码的可读性。

0 个答案:

没有答案