2013-03-01 94 views
1

我有一个一维函数需要花费很多时间来计算一个大的“x”值的二维数组,因此使用SciPy创建一个插值函数非常容易然后使用它来计算y,这会快得多。但是,我不能在具有多于一维的数组上使用插值函数。在二维数组上使用插值函数

例子:

# First, I create the interpolation function in the domain I want to work 
x = np.arange(1, 100, 0.1) 
f = exp(x) # a complicated function 
f_int = sp.interpolate.InterpolatedUnivariateSpline(x, f, k=2) 

# Now, in the code I do that 
x = [[13, ..., 1], [99, ..., 45], [33, ..., 98] ..., [15, ..., 65]] 
y = f_int(x) 
# Which I want that it returns y = [[f_int(13), ..., f_int(1)], ..., [f_int(15), ..., f_int(65)]] 

但回报:

ValueError: object too deep for desired array 

我知道我可以遍历所有的X成员,但我不知道这是否是一个更好的选择...

谢谢!

编辑:

像那样的功能也将做的工作:

def vector_op(function, values): 

    orig_shape = values.shape 
    values = np.reshape(values, values.size) 

    return np.reshape(function(values), orig_shape) 

我已经试过了,但np.vectorize是太慢了......

回答

2

如果f_int想一维数据,你应该扁平化你的输入,将其提供给内插,然后重建原来的形状:

>>> x = np.arange(1, 100, 0.1) 
>>> f = 2 * x # a simple function to see the results are good 
>>> f_int = scipy.interpolate.InterpolatedUnivariateSpline(x, f, k=2) 

>>> x = np.arange(25).reshape(5, 5) + 1 
>>> x 
array([[ 1, 2, 3, 4, 5], 
     [ 6, 7, 8, 9, 10], 
     [11, 12, 13, 14, 15], 
     [16, 17, 18, 19, 20], 
     [21, 22, 23, 24, 25]]) 
>>> x_int = f_int(x.reshape(-1)).reshape(x.shape) 
>>> x_int 
array([[ 2., 4., 6., 8., 10.], 
     [ 12., 14., 16., 18., 20.], 
     [ 22., 24., 26., 28., 30.], 
     [ 32., 34., 36., 38., 40.], 
     [ 42., 44., 46., 48., 50.]]) 

x.reshape(-1)做的展平,并且.reshape(x.shape)将其返回到其原始形式。

+0

那可能会给边缘带来怪异 – reptilicus 2013-03-01 17:31:02

+0

@reptilicus为什么?我似乎不明白你的意思,对不起... – Jaime 2013-03-01 17:34:27

+0

我在想,插值会导致原始数组边缘的值不同,一旦数组变平,然后插值然后重新变形。基本上,原始数组的左边将插入下一行的右边缘,这可能会或可能不会导致问题。 – reptilicus 2013-03-01 17:45:08

0

我会用一个list comprehensionmap的组合(可能有一种方法可以使用我缺少的两个嵌套的maps

In [24]: x 
Out[24]: [[1, 2, 3], [1, 2, 3], [1, 2, 3]] 

In [25]: [map(lambda a: a*0.1, x_val) for x_val in x] 
Out[25]: 
[[0.1, 0.2, 0.30000000000000004], 
[0.1, 0.2, 0.30000000000000004], 
[0.1, 0.2, 0.30000000000000004]] 

这仅仅是用于说明目的....更换lambda a: a*0.1与功能,f_int

1

我想你想要做一个量化的功能numpy的:

#create some random test data 
test = numpy.random.random((100,100)) 

#a normal python function that you want to apply 
def myFunc(i): 
    return np.exp(i) 

#now vectorize the function so that it will work on numpy arrays 
myVecFunc = np.vectorize(myFunc) 

result = myVecFunc(test)