该类为 Arduino 实现了一个简单的线性递归指数滤波器。它提供了一种简单的方法来平滑模拟传感器的噪声测量,而无需使用与移动平均滤波器一样多的内存。ExponentialFilter
过滤器的工作原理
每次您提供新值 (xn),则指数滤波器会更新平滑值 (yn):
这里:
- yn是滤波器在时间 n 中的某个时刻的输出
- xn是时间 n 中某个时刻的新输入值
- yn – 1是筛选器的上一个输出值
- w 是范围 [0, 100] 中的加权因子。
滤波器基本上会减慢对输入信号中快速变化(如噪声)的响应。
此图显示了滤波器权重 w 如何影响对输入信号中阶跃变化的响应。
较高的 w 值(例如 90)优先使用新数据而不是旧数据。输出对 input 的变化响应迅速,但不是很平滑。
较低的 w 值(例如 10)优先使用旧数据而不是新数据。滤波器输出被高度平滑,并且对输入中的变化 (嘈杂或无噪声) 做出缓慢响应。
滤波器会减慢对输入信号中阶跃变化(如噪声)的响应。红色粗线表示步进输入信号。当 w 较小时,输出信号需要多次测量才能到达输入信号。当 w 较大时,响应很快到达输入信号。
选择过滤器重量
选择合适的滤光片重量的一种直接方法是试验。
使用时间图可视化器绘制原始传感器数据和过滤的传感器数据。MegunoLink 中的两个值。通过观察不同的滤波器权重值如何影响信号来选择最佳滤波器。
下面的示例从 ADC 通道 0 读取传感器输出,并将原始信号和滤波信号发送到 MegunoLink 时间图。
来自 ADC 的原始测量值(绿色)由指数滤波器(红色)平滑处理
#include "MegunoLink.h"
#include "Filter.h"
// Create a new exponential filter with a weight of 5 and an initial value of 0.
long FilterWeight = 5;
ExponentialFilter<long> ADCFilter(FilterWeight, 0);
void setup()
{
Serial.begin(9600);
Serial.println("Exponential Filter demo");
Serial.println("-----------------------");
}
void loop()
{
int RawValue = analogRead(0);
ADCFilter.Filter(RawValue);
TimePlot Plot;
Plot.SendData("Raw", RawValue);
Plot.SendData("Filtered", ADCFilter.Current());
delay(100);
}
过滤多个信号
它是自包含的,因此如果您想过滤多个信号,您可以只使用多个实例。例如,此 Arduino 草图将前三个模拟输入的过滤版本发送到 MegunoLink 进行绘图。每个过滤器都有不同的权重。ExponentialFilter
#include "MegunoLink.h"
#include "Filter.h"
// Create three filters, one for each analog port monitored.
ExponentialFilter<long> Filter1(5, 0);
ExponentialFilter<long> Filter2(10, 0);
ExponentialFilter<long> Filter3(70, 0);
void setup()
{
Serial.begin(9600);
Serial.println("Multiple Filter demo");
Serial.println("--------------------");
}
void loop()
{
Filter1.Filter(analogRead(0));
Filter2.Filter(analogRead(1));
Filter3.Filter(analogRead(2));
TimePlot Plot;
Plot.SendData("A0", Filter1.Current());
Plot.SendData("A1", Filter2.Current());
Plot.SendData("A2", Filter3.Current());
delay(100);
}
Filter 函数参考
这是一个模板类,它采用单个参数:要筛选的度量类型。当前过滤的值在内部乘以 10 以提高过滤器的精度。通常使用 (如果您还没有使用浮点数,以节省代码空间) 或 (为了获得更准确的结果) 作为 filter 参数。ExponentialFilter
long
float
构造函数采用两个参数:
- 初始过滤器权重。此值应介于 0 和 100 之间
- 初始值。通常为 0。
使用以下方法声明新的指数滤波器:
#include "Filter.h"
// Create a new exponential filter with a weight of 5 and an initial value of 0.
ExponentialFilter<long> ADCFilter(5, 0);
筛选 (NewValue)
将筛选器应用于新值。请参阅下面的示例。
SetWeight(新权重)
更改筛选时应用的权重。此值应介于 0 和 100 之间。
高权重(例如 90)优先使用新数据而不是旧数据。因此,output 对 input 的变化响应迅速,并且不会被平滑太多。
较低的值 (10,例如) 优先使用旧数据而不是新数据。因此,输出被高度平滑,滤波器对输入中的变化(无论是否嘈杂)响应缓慢。
获取权重()
返回 filter weight 参数的当前值。
当前()
返回 filter 输出的当前值。
SetCurrent(新值)
强制当前值为提供的新值。通常用于从测量初始化滤波器。
可用性
指数滤波器包含在我们的 MegunoLink Arduino 库中,可以使用 Arduino 集成工具进行安装。
可参考以下链接安装
Installing the MegunoLink Arduino Library_哔哩哔哩_bilibili