三次样条外推法

时间:2009-05-19 05:52:21

标签: plot interpolation spline graphing extrapolation

我有一个很好的三次样条代码,但它仅用于插值。我需要extrapolate进入未来。这样做有没有人知道一个很好的代码来源,而不是一个库?

This is the code我在基本(现在的ASM)中写了插值。

5 个答案:

答案 0 :(得分:6)

您不需要新的代码。

要推断样条曲线,您可以推断第一个和最后一个样条曲线的参数

取决于您现有的代码/库,如果不修改代码,可能无法实现。在这种情况下,只需将两个其他点添加/添加到点列表的开头/结尾。您可以通过在第一个/最后两个点之间进行线性插值来获得这两个点。

小心:根据点的原始含义,外推可能完全不合适,特别是在统计数据方面。在这种情况下,您应该考虑使用regression analysis

答案 1 :(得分:3)

为简单起见,我将代表一个三次贝塞尔曲线 作为4分(A,B,C,D), 其中A和D是曲线的端点, B和C是“控制处理点”。 (实际曲线通常触摸控制手柄点)。

参见"Don Lancaster's Guru's Lair Cubic Spline Library" 用于转换这种三次贝塞尔曲线表示的方法 进入其他流行的陈述。

<强>插值

给出一个三次贝塞尔曲线(P0,P1,P2,P3), 我们使用De Casteljau's algorithm 切断Bezier曲线 左半部分和右半部分。 即使在没有“乘法”指令的微控制器上,这也非常简单, 因为它只需要计算一些平均值才能得到一个中点:

P0
   F0 := average(P0, P1)
P1                       S0 := average(F0, F1)
   F1 := average(P1, P2)         Midpoint := average(S0, S1)
P2                       S1 := average(F1, F2)
   F2 := average(P2, P3)
P3

整个贝塞尔曲线为(P0,P1,P2,P3)。

整个贝塞尔曲线的左半部分是贝塞尔曲线(P0,F0,S0,M)。

整个贝塞尔曲线的右半部分是贝塞尔曲线(M,S1,F2,P3)。

许多微控制器继续将每条曲线分开 变成越来越小的小曲线 直到每件都小到足以接近 一条直线。

但我们想要走另一条路 - 推断出更大的曲线。

<强>外推

鉴于左半部分或右半部分, 我们可以反过来运行它来恢复原始曲线。

让我们想象一下,我们忘记了原点P1,P2,P3。

给定贝塞尔曲线的左半部分(P0,F0,S0,M), 我们可以通过以下方式向右推断:

S1 := M + (M - S0)
F1 := S0 + (S0 - F0)
P1 := F0 + (F0 - P0)

然后使用这些值来计算

F2 := S1 + (S1 - F1)
P2 := F1 + (F1 - P1)

最后

P3 := F2 + (F2 - P2)

推断并恢复外推的Bazier曲线(P0,P1,P2,P3)。

<强>详情

外推曲线(P0,P1,P2,P3) 通过原始曲线中的每个点 (P0,F0,S0,M) - 特别是,从P0开始并经过中点M - 并一直持续到达P3。

我们总能从任意4点(P0,F0,S0,M)推断, 是否最初计算这4个点 作为一些较大的Bezier样条的左半部分(或右半部分)。

我相信你已经知道了这一点,但为了清楚起见:

Midpoint = average(F0, F1)

表示“在点F0和F1之间正好找到中点”, 或换句话说,

Midpoint.x = (F0.x + F1.x)/2
Midpoint.y = (F0.y + F1.y)/2
Midpoint.z = (F0.z + F1.z)/2

表达式

S1 := M + (M - S0)

表示“给定一个线段,一端在S0,中点在M, 从S0开始,沿着直线经过M直到你到达另一端S1“, 或换句话说 (除非你有一个像样的矢量库)3行代码

S1.x := M.x + (M.x - S0.x)
S1.y := M.y + (M.y - S0.y)
S1.z := M.z + (M.z - S0.z)

。 (如果你正在做2D,跳过所有“z”的东西 - 它总是为零)。

答案 2 :(得分:2)

你真的必须稍微扩展这个问题。此外,“三次样条”是一个非常宽泛的术语。

如果您对样条线感兴趣,我可以衷心地推荐Carl de Boors“Splines实用指南”。然而,它有点数学导向,但它包含代码示例(可以从作者的主页下载)。谷歌搜索和维基“三维样条”可以提出一些例子,甚至可能在特定的语言中 - 另一个问题是添加到问题中(如果你正在寻找代码)。

如果您对外推和曲线拟合感兴趣,谷歌搜索可能会有所帮助。 Matlab包有一个非常漂亮的曲线拟合工具箱。维基百科有一些指向有用参考的链接

真的,这个问题太宽泛了,甚至开始猜测答案。

另外,你能解释一下你到底想要做什么吗?什么样的数据?什么?


Edit1:在这里,试试这个:你可以在这里找到一些有用的东西 - link

答案 3 :(得分:1)

通常,对于样条插值,您可以使用变量t对线进行插值。只要0 <= t <= 1,就进行插值。但是,当t < 0或t> 1你只是简单地推断样条曲线。

答案 4 :(得分:0)

您需要为请求的代码编写更好的要求。样条通常用于通过使用某些固定数据集来插入某些未知或复杂函数。如果要在此数据集的边界之外估计函数的值,则不应使用样条曲线。

如果您的样条函数在您真正想要评估值的位置定义(立方体,而不是分段立方体),那么您已经可以评估该值。

如果您希望能够在插值范围之外评估样条曲线,但将其保留为在插值范围内具有相同值的分段三次函数,则应该通过某些节点扩展样条曲线范围,并添加一些评估逻辑新节点处的值(例如,您希望样条不仅是连续函数,而且还有一些一阶导数也是连续函数)

我真的建议你使用一些更适合外推的算法,比如使用Lagrange polynomial,如果你真正需要的是单个值,距离原始数据集的点不是很远。