如何通常实现数据集的线性插值?

时间:2015-03-24 00:22:17

标签: javascript math interpolation

假设如果给出(x,y)值中的一堆点,并且需要通过在x轴中的2个最近值之间线性插值来生成点,那么最快的实现是什么?

我四处寻找,但我找不到满意的答案,我觉得这是因为我没有找到合适的词语。

例如,如果我被给予(0,0)(0.5,1)(1,0.5),那么我想得到一个0.7的值;它将是(0.7-0.5)/(1-0.5)*(0.5-1)+ 1;但是什么数据结构可以让我找到两个最接近的键值来插入?如果我能够做到最好的关键值,那么这是一个简单的线性搜索/二进制搜索吗?

2 个答案:

答案 0 :(得分:2)

我通常实现O(1)插值的方式是通过一个额外的数据结构,我称之为IntervalSelector,在时间O(1)将给出必须的序列的两个周围值内插。

IntervalSelector是一个类,当给出sequence n个横坐标时,会记住一个table,它会映射x的任何给定值到索引i,使sequence[i] <= x < sequence[i+1]在时间O(1)。

注意:以下内容数组基于1。

构建表的算法如下:

  1. delta视为横坐标输入sequence中两个连续元素之间的最小距离。
  2. 设置count := (b-a)/delta + 1,其中ab分别是(升序)sequence的第一个和最后一个,/代表整数商分裂。
  3. table定义为Arraycount元素。
  4. i1之间的n设置table[(sequence[j]-a)/delta + 1] := j.
  5. 将4中访问过的table的每个条目重复到其后的未访问位置。
  6. 在输出时,如果table

    ,则ji映射到(j-1)*d <= sequence[i] - a < j*d.

    以下是一个例子:

    enter image description here

    由于元素3 rd 和4 th 是最接近的元素,我们将该区间划分为该最小长度的子区间。现在,我们在table中记住每个deta-区间左端的位置。稍后,当给出输入x时,我们将此delta-的{​​{1}}间隔计算为x,并使用该表推导序列中的相应间隔。如果(x-a)/delta + 1落在x序列元素的左侧,我们会选择i

    更确切地说:

    如果(i-1)x之间的任何输入a计算bj := (x-a)/delta + 1如果i := table[j].x < sequence[i]。然后,索引i := i - 1满足i;否则这两个连续元素之间的距离将小于sequence[i] <= x < sequence[i+1],而不是。{/ p>

    备注:请注意,如果delta中连续元素之间的最小距离delta太小,则表格将包含太多条目。我在这里介绍的简单描述忽略了这些需要额外工作的病理情况。

答案 1 :(得分:1)

是的,一个简单的二进制搜索应该做得很好,通常就足够了。

如果你需要变得更好,你可以尝试interpolation search(与你的值插值无关)。

如果您的点以固定间隔分布(如示例中的0 0.5 1),您还可以简单地将值存储在数组中,并通过索引以恒定时间访问它们。