C# - 通过二次拟合

问题描述:

我工作的一个算法来找到一个List对象峰找到一个给定的宽度内的峰。我认为我认为这是一个好的(或足够好的)算法,通过查看一个点,它是邻居,如果它是一个高峰,将它添加到结果列表中。但是,鉴于最近的一些结果,我认为这种方法不像我最初希望的那样工作。 (我已经包含了我目前使用的代码,并希望在下面进行替换)。我之前已经使用LabView做了一些工作,并且我知道他们的模块发现峰/谷的方式适用于我需要做的事情。我做了一些研究,LabVIEW如何做到这一点,发现这个:C# - 通过二次拟合

“这个峰值检波器VI是基于适合二次多项式的数据点的连续组的算法配合使用的数据点的数量。由宽度指定

对于每个峰或谷,将对照阈值对二次拟合进行测试,高度低于阈值的峰或谷值高于阈值的谷被忽略,峰和谷仅在VI处理大约宽度/ 2个数据点,超出峰值或谷值的位置。这种延迟仅影响实时处理。“

好了,现在我一直试图做的在C#中类似的东西,但是,在我所有的搜索似乎是一个二次多项式拟合数据肯定是不平凡的。我认为这个问题会被探索很多次,但是我一直没有成功地找到一个能很好地完成这项工作的算法,或者找到一个能够实现这个目标的库。

这个问题的任何帮助是极大的赞赏。谢谢。

原始/目前代码:

public static List<double> FindPeaks(List<double> values, double rangeOfPeaks) 
{ 
    List<double> peaks = new List<double>(); 

    int checksOnEachSide = (int)Math.Floor(rangeOfPeaks/2); 
    for (int i = checksOnEachSide; i < values.Count - checksOnEachSide; i++) 
    { 
     double current = values[i]; 
     IEnumerable<double> window = values; 
     if (i > checksOnEachSide) 
      window = window.Skip(i - checksOnEachSide); 
     window = window.Take((int)rangeOfPeaks); 
     if (current == window.Max()) 
      peaks.Add(current); 
    } 
    return peaks; 
} 

我在C#中使用Math.NET的矩阵运算这样的。它具有您可能需要的最小二乘问题的所有工具,如QR分解或SVD。对于如何应用它们的一般概述,我认为wikipedia做得不错。