You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
209 lines
5.7 KiB
209 lines
5.7 KiB
#pragma once
|
|
#include <fstream>
|
|
#include <functional>
|
|
#include <iostream>
|
|
#include <list>
|
|
#include <map>
|
|
#include <memory>
|
|
#include <set>
|
|
#include <sstream>
|
|
#include <string>
|
|
#include <vector>
|
|
namespace opt_algo {
|
|
using namespace std;
|
|
|
|
|
|
typedef enum {
|
|
k250,
|
|
k1000,
|
|
} ProcessPointNumType_t;
|
|
|
|
typedef enum {
|
|
k_ecode_ok = 0,
|
|
k_ecode_can_not_find_peak = 1,
|
|
k_ecode_can_not_find_peak_start = 2,
|
|
k_ecode_can_not_find_peak_end = 3,
|
|
} Error_t;
|
|
|
|
class LineContext {
|
|
public:
|
|
vector<float> raw; //
|
|
vector<float> avg; //
|
|
vector<float> diff; //
|
|
float agvline; //
|
|
float baseline_slope; //
|
|
float baseline_intercept; //
|
|
|
|
vector<float> raw250; //
|
|
vector<float> avg250; //
|
|
vector<float> diff250; //
|
|
};
|
|
|
|
class PeakInfo {
|
|
public:
|
|
bool find_peak;
|
|
float peak_full_area;
|
|
float peak_base_line_area;
|
|
float area;
|
|
int peak_pos;
|
|
int peak_start_pos;
|
|
int peak_end_pos;
|
|
};
|
|
|
|
class AlgoResult {
|
|
public:
|
|
/**
|
|
* @brief
|
|
* 原始数据处理逻辑:
|
|
* 1) 1200点中值滤波
|
|
* 2) 1200点线性填充到6000点
|
|
* 3) 6000点窗口平滑滤波
|
|
* 4) 6000点均值压缩到1000点
|
|
*
|
|
* 5) 1000点 13点滑动均值滤波
|
|
* 6) 1000点 20点最小二乘法求斜率
|
|
*
|
|
* 7) 找峰
|
|
* 8)找峰起始位
|
|
* 9) 找峰结束位
|
|
*
|
|
*/
|
|
AlgoResult() {
|
|
error_code = k_ecode_ok;
|
|
lineContext = make_shared<LineContext>();
|
|
for (int i = 0; i < 5; i++) {
|
|
peakInfo[i] = make_shared<PeakInfo>();
|
|
}
|
|
}
|
|
vector<float> ogigin_val; // 1200
|
|
vector<float> supper_val; // 原始数据,线性填充,1200*5=6000
|
|
vector<float> supper_median_val; // supper_val 窗口平滑滤波,6000
|
|
vector<float> supper_smooth_sub_val; // supper_smooth_val 均值压缩,6000/6=1000
|
|
|
|
shared_ptr<LineContext> lineContext; // supper_smooth_sub_val 13点滑动均值滤波,1000
|
|
|
|
Error_t error_code; // 错误码
|
|
|
|
// result
|
|
shared_ptr<PeakInfo> peakInfo[5];
|
|
int peakNum;
|
|
};
|
|
|
|
class OptAlgo {
|
|
public:
|
|
/**
|
|
* @brief
|
|
*
|
|
* @param context
|
|
* @param pconfig
|
|
* @param ogigin_val expect 1200
|
|
*/
|
|
static shared_ptr<AlgoResult> calculate(vector<float> ogigin_val, int peaknum);
|
|
static int calculate_peak_num(vector<float>& ogigin_val);
|
|
|
|
static int getAlgoVersion();
|
|
|
|
private:
|
|
static Error_t findpeak(shared_ptr<LineContext> lineContext, int32_t search_start, int32_t peakwindth, shared_ptr<PeakInfo> retpeak);
|
|
static int sub_find_peak(shared_ptr<LineContext> lineContext, int start_off, int windos_size, int judge_win_size);
|
|
static int find_peak_endpoint(shared_ptr<LineContext> lineContext, int peakpos, int search_direction, int search_windows);
|
|
|
|
private:
|
|
/*******************************************************************************
|
|
* 基础方法 *
|
|
*******************************************************************************/
|
|
|
|
/**
|
|
* @brief 过采样原始数据
|
|
*
|
|
* @param inputRaw
|
|
* @param nInputLength
|
|
* @param nUpSampleRate
|
|
* @return vector<float>
|
|
*/
|
|
static vector<float> super_sampling(vector<float>& inputRaw, int32_t nInputLength, int32_t nUpSampleRate);
|
|
/**
|
|
* @brief 均值压缩数据
|
|
*
|
|
* @param inputRaw
|
|
* @param nSubSampleRate
|
|
* @return vector<float>
|
|
*/
|
|
static vector<float> sub_sampling(vector<float>& inputRaw, int nSubSampleRate);
|
|
/**
|
|
* @brief 移动窗口平滑数据
|
|
*
|
|
* @param inputRaw
|
|
* @param windows_size
|
|
* @return vector<float>
|
|
*/
|
|
static vector<float> smooth_windows(vector<float>& inputRaw, int windows_size);
|
|
|
|
/**
|
|
* @brief 移动窗口平滑数据
|
|
*
|
|
* @param inputRaw
|
|
* @param windows_size
|
|
* @return vector<float>
|
|
*/
|
|
static vector<float> median_filtering(vector<float>& inputRaw, int windows_size);
|
|
/**
|
|
* @brief 计算均值线
|
|
*
|
|
* @param inputRaw
|
|
* @return float
|
|
*/
|
|
static float find_avg_line(vector<float>& inputRaw);
|
|
/**
|
|
* @brief 简单曲线求导
|
|
*
|
|
* @param inputRaw 原始数据
|
|
* @return vector<float> 和原始数据等长导数曲线
|
|
*/
|
|
static vector<float> differentiate(vector<float>& inputRaw);
|
|
/**
|
|
* @brief 最小二乘法求导
|
|
*
|
|
* @param inputRaw 原始数据
|
|
* @param windows_size 窗口大小
|
|
* @return vector<float> 和原始数据等长导数曲线
|
|
*/
|
|
static vector<float> least_square_method_differentiate(vector<float>& inputRaw, int windows_size);
|
|
|
|
/**
|
|
* @brief 当前数值是否是窗口内最大值(往前windsize/2,往后windowsize/2)
|
|
*
|
|
* @param val 当前数值指针
|
|
* @param windows_size 窗口大小,必须是奇数
|
|
* @return true
|
|
* @return false
|
|
*/
|
|
static bool is_maxval_in_windows(float* val, int windows_size);
|
|
/**
|
|
* @brief 比较两个浮点数是否相等
|
|
*
|
|
* @param a
|
|
* @param b
|
|
* @param epsilon
|
|
* @return true
|
|
* @return false
|
|
*/
|
|
static bool feq(float a, float b, float epsilon = 0.00001);
|
|
/**
|
|
* @brief 最小二乘法 求一次函数斜率
|
|
*
|
|
* @param val
|
|
* @param size
|
|
* @return float
|
|
*/
|
|
static void linear_least_squares(vector<float>& x, vector<float>& y, float& slope, float& intercept);
|
|
static void linear_least_squares(float* y, int size, float& slope, float& intercept);
|
|
static void linear_least_squares_muti_windos(float* y, int size, vector<int> startx, int windowssize, float& slope, float& intercept);
|
|
|
|
static float get_avg_in_windows(vector<float>& src, int off, int windows);
|
|
|
|
static void sort_vector(vector<float>& src);
|
|
static vector<float> getwindowspoint(vector<float>& src, int off, int windows);
|
|
};
|
|
|
|
} // namespace opt_algo
|