历史上的今天
今天是:2025年03月31日(星期一)
2020年03月31日 | 单片机ADC采样算法----卡尔曼滤波
2020-03-31 来源:eefocus
关于卡尔曼滤波,看看百度百科上的定义

算法的核心思想是,根据当前的仪器"测量值" 和上一刻的 "预测量" 和 "误差",计算得到当前的最优量.
再预测下一刻的量, 里面比较突出的是观点是. 把误差纳入计算, 而且分为预测误差和测量误差两种.通称为 噪声. 还有一个非常大的特点是,误差独立存在, 始终不受测量数据的影响。
下来先了解一个卡尔曼滤波中几个参数的含义:概率(Probability),随即变量(Random Variable),高斯或正态分配(Gaussian Distribution)还有State-space Model等等。
关于卡尔曼公式的含义及推导,网上已经有很多文章了,这里不在赘述,直接看C代码的实现。
/*
R值固定,Q值越大,代表越信任测量值,Q值无穷大,代表只用测量值。
Q值越小,代表越信任模型预测值,Q值为0,代表只用模型预测值。
*/
//参数一
float KalmanFilter( float inData )
{
static float prevData = 0; //上一个数据
static float p = 10, q = 0.001, r = 0.001, kGain = 0; // q 控制误差 r 控制响应速度
p = p + q;
kGain = p / ( p + r ); //计算卡尔曼增益
inData = prevData + ( kGain * ( inData - prevData ) ); //计算本次滤波估计值
p = ( 1 - kGain ) * p; //更新测量方差
prevData = inData;
return inData; //返回估计值
}
现在测试一下卡尔曼滤波的效果,通过函数发生器产生一个锯齿波,送到单片机的AD口,单片机读取采集到的AD数据后,经过卡尔曼滤波算法,然后将采样的数据和滤波后的数据通过串口发生出来,并在串口波形显示软件上显示。
void main( void )
{
while( 1 )
{
val1 = ReadVol_CH3(); //读取AD采样数据
dat = ( float )val1;
dat = KalmanFilter( dat ); //卡尔曼滤波
printf("A%drn",val1); //打印结果
printf("B%2frn",dat);
}
}
现在看一下滤波的结果

蓝色曲线为原始采样的数据曲线,橙色曲线为经过卡尔曼滤波后的曲线。
下面改变Q和R的值在测试一下滤波效果。
修改后的参数如下
//参数二
unsigned long kalman_filter( unsigned long ADC_Value )
{
float LastData;
float NowData;
float kalman_adc;
static float kalman_adc_old = 0;
static float P1;
static float Q = 0.0003;
static float R = 5;
static float Kg = 0;
static float P = 1;
NowData = ADC_Value;
LastData = kalman_adc_old;
P = P1 + Q;
Kg = P / ( P + R );
kalman_adc = LastData + Kg * ( NowData - kalman_adc_old );
P1 = ( 1 - Kg ) * P;
P = P1;
kalman_adc_old = kalman_adc;
return ( unsigned long )( kalman_adc );
}
测试波形

蓝色曲线为原始采样的数据曲线,橙色曲线为经过卡尔曼滤波后的曲线。
和第一次测试的波形图对比后可以发现,第二次经过卡尔曼滤波后的波形变化非常大,参数改变后锯齿波被滤成接近于直线了。
可以看到不同的R、Q值会对测量结果有很大的影响。
Q:过程噪声,Q增大,动态响应变快,收敛稳定性变坏
R:测量噪声,R增大,动态响应变慢,收敛稳定性变好
具体各个参数的如何选择,只有在应用中根据测量结果,自己慢慢调整。目前还没有找到权威的资料来讲解这些参数如何选择。
史海拾趣
|
【原创】可调电阻的 介绍 选用以及使用方法 可调电阻与电位器的区别与联系 http://blog.ednchina.com/freeeedoooom/187414/message.aspx… 查看全部问答> |
|
求助:CodeWarrior for ADS 1.2中编译出错 工程中,用ADS编译,出现了Errors: Could not find or load the file 襐IC.a?for target 褼ebugRel?for project 襱est1.mcp? Could not find or load the file 褻omm.a?for target 褼ebugRel?for project 襱est1.mcp? The following access p ...… 查看全部问答> |
|
如题,想了解下目前PPC或者SmartPh上播放mp3格式的音频文件主要用哪种技术?windows media sdk? DirectShow? 或者其他的第三方控件? (当然需要免费的)… 查看全部问答> |
|
1.第一忌 自己不动脑筋,一遇到问题就问别人有句话说的好“吃别人咀嚼过的馍不香”。对于新手来说,做每一件事都是一次学习的好机会。有时候,探索的过程比最终的结果更重要。当你经过自己的努力,解决问题时,成就感和自信心会随之逐渐建立。如果 ...… 查看全部问答> |
|
今早用altium designer6.9画原理图时突然出现了这么一个问题··不得其解啊 就是我放置导线时··本来把我想要连接上的两个引脚端连上就可以了··可是呢··导线的终点却与多个引脚连到一起了··自动产生了很多我不想要连接上的节点··这是怎么回事呢?之前放导线的时候貌似没出现这情况··… 查看全部问答> |
|
大家有没有仔细研究这个电源的EMI测试曲线(见图1)呢,这个曲线的首段在150-600KHz中,红线以下的EMI测试曲线峰值超越或者接近红线(所谓的红线:就是电源板PCBA的EMI测试曲线的电磁兼容的合格与否的界限),为了说明问题特意将低频段的EMI做的高 ...… 查看全部问答> |




