如何评估splprep的样条导数?

时间:2017-07-14 13:31:30

标签: python scipy interpolation

我希望使用B样条计算numpy中闭合曲线的曲率。我想评估样条曲线表示的导数而不是数据,以获得平滑的结果。但是,下面的代码会返回错误:

    Traceback (most recent call last):
      File "<stdin>", line 16, in <module>
      File "/Users/jfl/anaconda/lib/python2.7/site-packages/scipy/interpolate/fitpack.py", line 1212, in splder
        c = (c[1:-1-k] - c[:-2-k]) * k / dt
    TypeError: unsupported operand type(s) for -: 'list' and 'list'

shell returned 1

所以我想知道我是否正确使用splder功能......

import numpy as np
import scipy.interpolate as intplt
import matplotlib.pyplot as plt


t = np.linspace(0,2*np.pi,100)
x = np.cos(t)
y = np.sin(t)


pts = np.vstack((x,y))
tck, u = intplt.splprep(pts, u=None,k=3, s=0.0, per=1)
u_new = np.linspace(u.min(), u.max(), 1000)
x_new, y_new = intplt.splev(u_new, tck, der=0)

tck_der1 = intplt.splder(tck)
tck_der2 = intplt.splder(tck_der1)


xp, yp = intplt.splev(u_new, tck_der1, der=0)
xpp, ypp = intplt.splev(u_new, tck_der2, der=0)



plt.figure()
plt.plot(x,y,".")
plt.plot(x_new,y_new)

plt.figure()
curvature = np.abs(xp* ypp - yp* xpp) / np.power(xp** 2 + yp** 2, 3 / 2)
plt.plot(u_new,curvature)

plt.show()

1 个答案:

答案 0 :(得分:1)

splder仅支持标量样条线(使用y = f(x)插入函数splrep),而不支持使用splprep获得的矢量样条线。在任何情况下,您都不需要它:只需使用der的{​​{1}}参数:

splev

这不是导数的一般有限差分评估; xp, yp = intplt.splev(u_new, tck, der=1) xpp, ypp = intplt.splev(u_new, tck, der=2) 实际上会使用样条结构来计算它,这就是你想要做的事情。

我猜你尝试了上述内容并对输出感到不满:

output

但这只是Matplotlib很有趣。绘图窗口从+ 9.998e-1到+ 9.998e-1 + 0.0006。换句话说,曲率几乎是恒定的(1),因此matplotlib放大了来自插值的不可避免的噪声。只需设置合理的绘图窗口,问题就会消失。

nice

(或者,使用像splev这样的例子来获得漂亮的非常数曲率。)