用可变输入时间平滑数字的算法

时间:2012-01-14 23:15:09

标签: algorithm

我有一个应用程序,每隔0.25到2秒以可变速率接受整数。

我希望以平滑的格式输出数据3秒,5秒或7秒,具体取决于用户输入。

如果数据始终以相同的速率进入,那么假设每隔0.25秒,那么这将很容易。可变利率使我感到困惑。

数据可能会像这样出现:
时间 - 数据
0.25 - 100
0.50 - 102
1.00 - 110
1.25 - 108
2.25 - 107
2.50 - 102
等...

我想在我的显示器上每隔0.25秒显示3秒滚动平均值。

最简单的方法是将每个项目放入带有时间戳的数组中。

array.push([0.25, 100])  
array.push([0.50, 102])  
array.push([1.00, 110])  
array.push([1.25, 108])  

等...

然后每隔0.25秒,我会读回数组,然后回到前面,直到我达到小于now() - rollingAverageTime的时间。我会总结并显示它。然后我会.Shift()数组的开头。

虽然看起来效率不高。我想知道是否有人有更好的方法来做到这一点。

3 个答案:

答案 0 :(得分:2)

为什么不保存起始值的时间戳,然后累积值和样本数,直到获得>= startingTime + rollingAverageTime的时间戳,然后将累加器除以采样数?

编辑: 如果要保留样本数,可以这样做:

取累加器,并为每个输入值求和,并将值和时间戳存储在移位寄存器中;在每个周期,您必须将最新样本的时间戳与移位寄存器中最旧的时间戳加上平滑时间进行比较;如果它等于或大于等于,则从累加器中减去最早保存的值,从移位寄存器中删除该条目并输出累加器,除以平滑时间。如果你迭代,你得到一个滚动平均值(我认为)每个周期的计算量最小:

  • 总和(增加累加器)
  • 和和减法(比较时间戳)
  • 减法(来自累加器)
  • 一个师(计算平均值,以聪明的方式完成,可以是右移)

总共约4个代数和一个除法(或移位)

编辑:

考虑到从最后一个样本作为加权因子的时间,您可以将此时间与平均时间之间的比率值除以,并获得已经加权的平均值,而不必分割累加器。 / p>

我添加了这部分,因为它没有增加计算负荷,所以如果你愿意,你可以很容易地实现。

答案 1 :(得分:0)

clabacchio的答案基本正确,但也许你需要更复杂的答案。

计算平均值:

0.25 - 100
0.50 - 102
1.00 - 110

在上面的数据子集中,您想要的答案是什么?你可以使用这些数字的平均值,或者你可以用加权的方式来做。您可以将数据转换为:

0.50 - 0.25 = 0.25  ---- (100+102)/2 = 101
1.00 - 0.50 = 0.50  ---- (102+110)/2 = 106

然后你可以得到这些值的加权平均值,权重是时差,值是平均值。

最终答案=(0.25 * 101 + 0.5 * 106)/(0.25 + 0.5)=无论值是什么。

现在开始“移动”平均值:

您可以使用之前的k值或之前的k秒数据。在这两种情况下,您都可以保留两个总和:加权和和权重之和。

答案 2 :(得分:0)

所以......最糟糕的情况是7秒钟内每秒4个读数=你要处理的数组中的28个值。无论如何,这将在几纳秒内完成,因此不值得优化恕我直言。