python

时间:2015-09-12 20:08:58

标签: python numpy scipy integral

我有一组点,在这些点上我使用scipy来计算插值多项式。我希望拥有该功能的原语

self.p=interpolate.interp1d(self.__discreteDistribution['x'], self.__discreteDistribution['y'], kind='cubic')

我可以轻松地使用scipy来计算一个区间内积分的,使用

integrate.quad(self.p, 0, max)

我想要的是拥有self.p()的原语。 我找到了同情,但我没有插值多项式的分析版本。

在这些场合你会做什么?

2 个答案:

答案 0 :(得分:3)

假设您正在使用分段插值器(而不是全局多项式插值),有几种方法可以用scipy来实现:

方法1:UnivariateSpline。

In [1]: import numpy as np

In [2]: x = np.arange(8)

In [3]: y = x

In [4]: from scipy.interpolate import interp1d

In [5]: from scipy.interpolate import interp1d, UnivariateSpline

In [6]: spl = UnivariateSpline(x, y, s=0)

In [7]: spl.<TAB>
spl.antiderivative        spl.get_coeffs            spl.roots
spl.derivative            spl.get_knots             spl.set_smoothing_factor
spl.derivatives           spl.get_residual          
spl.ext                   spl.integral              

In [8]: spl.integral(0, 1)
Out[8]: 0.5000000000000001

UnivariateSpline的两个怪癖:首先,使用s=0进行插值(而不是最小二乘拟合)。其次,要注意外界的推断。默认情况下,UnivariateSpline推断越界值(这可以在构造函数中控制),但.integral假定样条曲线超出界限。

In [9]: spl.integral(-1, 1)
Out[9]: 0.5000000000000001

方法2:splev,splrep和splint。

In [13]: from scipy.interpolate import splev, splint, splrep

In [14]: tck = splrep(x, y, s=0)

In [15]: splint(0, 1, tck)
Out[15]: 0.5000000000000001

这相当于使用UnivariateSpline,只是界面有点不同。有关详细信息,请参阅文档。

方法3:interp1d。

在幕后,interp1d也使用b样条(除非你请求kind ='linear'或'nearest'),但评估例程是不同的。 interp1d构造一个可调用的,然后可以将其提供给通用的积分器。

In [18]: from scipy.interpolate import interp1d

In [19]: interp = interp1d(x, y, kind='cubic')

In [20]: from scipy.integrate import quad

In [21]: quad(interp, 0, 1)
Out[21]: (0.5000000000000024, 5.5511151231258095e-15)

再次注意越界值:interp1d构造的结果的行为不是很有用(即使它在一定程度上是可控的)。

答案 1 :(得分:1)

interp1d method似乎只为您提供插值函数的函数对象,它允许您评估任意函数值。

查看文档,我看不到内部表示的接口。 我猜它是分段定义的三次多项式的总和。 在这种情况下,您的基元将是分段定义的二次多项式的总和。这真的对你有用吗?

除了直接计算样条线(如askewchan的评论中所示),您可以尝试使用approximate_taylor_polynomialdoc)的函数值重新取样并获取poly1d(doc)每个子区间上的对象然后在每个子区间上使用poly1d.integdoc)来获取基元的系数。