我有一组数据,y是角度方向,x是y每个点的时间戳。
整个数据集有许多用于角度方向的分段。为了进行曲线拟合,我将数据拆分为各自的段,将每个段存储为numpy数组。
然后我使用numpy.polyfit找到多项式拟合,以找到适合每个数据段的曲线。但是因为我的数据纯粹是实验性的,所以我不知道numpy.polyfit使用哪个多项式度数,因此我迭代一系列多项式度,直到找到最高的多项式度。
这是我的代码:
pip3 install --upgrade pip
这就是我的情节。图中心是一个部分。
如图所示,黑色曲线拟合线并不能很好地拟合数据点。我感兴趣的区域是该区域的中间区域,但是尽管使用了最高的多项式度,该区域也不能很好地拟合。
任何人都可以向我提供任何补充技术,或者更适合数据的替代代码吗?
答案 0 :(得分:1)
数据的三次插值怎么样?
import numpy as np
from scipy.interpolate import interp1d
import matplotlib.pyplot as plt
x = np.linspace(6, 13, num=40)
y = 3 + 2.*x+np.sin(x)/2.+np.sin(4*x)/3.+ np.random.rand(len(x))/3.
fig, ax = plt.subplots()
ax.scatter(x,y, s=5, c="crimson")
f = interp1d(x, y, kind='cubic')
xdens = np.linspace(6, 13, num=400)
ydens = f(xdens)
ax.plot(xdens, ydens, label="interpolation")
ax.legend()
ax2 = ax.twinx()
yderiv = np.diff(ydens)/np.diff(xdens)
ax2.plot(xdens[:-1],yderiv, color="C2", label="derivative")
ax2.legend()
plt.show()
使用样条插值可以实现相同的效果。优点是scipy.interpolate.splrep
允许使用参数s
来平滑结果,并且还允许直接评估样条的导数。
import numpy as np
import scipy.interpolate
import matplotlib.pyplot as plt
x = np.linspace(6, 13, num=40)
y = 3 + 2.*x+np.sin(x)/2.+np.sin(4*x)/3.+ np.random.rand(len(x))/3.
fig, ax = plt.subplots()
ax.scatter(x,y, s=5, c="crimson")
tck = scipy.interpolate.splrep(x, y, s=0.4)
xdens = np.linspace(6, 13, num=400)
ydens = scipy.interpolate.splev(xdens, tck, der=0)
ax.plot(xdens, ydens, label="spline interpolation")
ax.legend(loc=2)
ax2 = ax.twinx()
yderiv = scipy.interpolate.splev(xdens, tck, der=1)
ax2.plot(xdens, yderiv, color="C2", label="derivative")
ax2.legend(loc=4)
plt.show()