卡尔曼滤波及MATLAB程序

转载 张文宇的博客   https://blog.csdn.net/zhangwenyu111/article/details/17034813

卡尔曼滤波是一个很常用的滤波算法,与维纳滤波相比有很多长处。这里我们把Kalman Filter简称为KF。KF的基本思想是:采用信号、噪声、状态空间模型,利用前一时刻的状态最优估计值及其误差方差估计和现时刻的量测值来更新对状态变量的估计,求出现在时刻的最优估计值。

说白点就是对现在时刻的估计(可能是同时估计好几个变量)是取决于前一时刻估计误差和现在时刻的某个观测值。通过不断的预测和实测来修正自己的估计值,最后达到一个理想的平稳状态。

卡尔曼滤波的具体原理和推导过程,有点复杂。某些细节我也没弄明白,不过这并不影响我们写程序和使用它。如果你看了我写的这个小分享,表明你对卡尔曼滤波有一定的了解了,否则你也不会看这种玩意。如果真的不了解,那可以查找下相关资料。

卡尔曼滤波的5大公式:

这五个公式公式可要注意他们的下标了,下面我们从上至下依次说下这五个公式的意思

第一个公式就是说我们研究的变量在这一时刻与上一时刻的具体关系。那个Fai矩阵就是系数对应关系。可以看到这里就把卡尔曼滤波的使用范围限定在线性系统中了,基本的卡尔曼滤波器是不能用于非线性系统的。

第二个公式叫方差先验估计,说的这么文艺,其实就是计算估计值和实际值的方差大小,以评估现在的估计的误差是不是合适。

第三个公式叫增益矩阵,前面已经说过,卡尔曼滤波根据当前观测变量的变化趋势来估计一时刻变量的值,这个增益矩阵就是指我们定的这个变化的“度”的大小。

第四个就是求要估计的值了。

第五个是修正估计值与实际值的方差。

这5个公式是卡尔曼滤波的关键,下面就结合一个实例在说下卡尔曼滤波的程序如何写~交大的同学,如果你们选了最优估计这门课,然后看到这个,嘿嘿,便宜你们了。

 

应用:卡尔曼滤波在目标测量中的应用

某火箭在空中沿直线做匀加速飞行,加速度为  ,发动机推力的波动一定会引起加速度波动,雷达以间隔时间不断测量该火箭距离远点的距离  ,由于雷达的测量噪声使得火箭距离测量值   中含有噪声。现在欲通过雷达对火箭距离的测量数据求得火箭的真实距离、速度和加速度。
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%     设置初始化信息
%  N:设置卡尔曼滤波器追踪点数
%  r:设置估计变量个数,这里r=3
%  s:被追踪的火箭的距离,初始值为1000m
%  v:火箭的速度,初始值为50m/s
%  a:火箭的加速度,初始值为20m/s2,此时加速度默认为不变
%  T: 雷达的扫描间隔,此时设为1秒
%  wt: 系统噪声,方差为20
%  vt: 量测噪声,方差为16
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
clear all;
close all;
N = 100;
r = 3;
t = 1:1:N;
T = 1;
s = zeros(1,N);
v = zeros(1,N);
a = zeros(1,N);
a(t) = 20;
s0 = 1000;
v0 = 50;
for n = 1:N
    v(n) = v0 + a(n)*n;
    s(n) = 1000+v0*n+0.5*a(n)*n*n;
end
wt = randn(1,N);
wt = sqrt(4)*wt./std(wt);
s = s + wt;
v = v + wt;
a(t) = a(t) + wt(t);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% 卡尔曼滤波部分,继承之前初始化变量
% A:转移矩阵
% H:量测矩阵
% Qk:系统噪声矩阵
% Rk:量测噪声矩阵
% P0:均方误差矩阵初始值
% Y:火箭的状态矩阵,由k_s,k_v,k_a组成
% Y0:状态矩阵的初始值
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
Y0 = [900 0 0]';
Y = [Y0 zeros(r,N-1)];
A = [1 1 0;0 1 1;0 0 1];
H = [1 0 0];
Qk = [0 0 0;0 0 0;0 0 20];
Rk = 16;
P0 = [30 0 0;0 20 0;0 0 10];
P1 = P0;
P2 = zeros(r,r);
for k = 1:N
    Y(:,k) = A*Y(:,k);
    P2 = A*P1*A'+Qk;
    Kk = P2*H'*inv(H*P2*H'+Rk);
    Y(:,k+1) = Y(:,k)+Kk*(s(:,k)-H*Y(:,k));
    P1 = (eye(r,r)-Kk*H)*P2;
end
k_s = Y(1,:);
k_v = Y(2,:);
k_a = Y(3,:);
subplot(3,1,1);
plot(t,s(t),'-',t,k_s(t),'o');
title('距离');
legend('实际值','估计值');
xlabel('t');
ylabel('s');
subplot(3,1,2);
plot(t,v(t),t,k_v(t),'+');
title('速度');
legend('实际值','估计值');
xlabel('t');
ylabel('v');
subplot(3,1,3);
plot(t,a(t),t,k_a(t),'-x');
title('加速度');
legend('实际值','估计值');
xlabel('t');
ylabel('a');
axis([0,N,0,30]);

基于卡尔曼滤波Matlab程序可以用于估计系统状态,特别是在存在噪声和不确定性的情况下。下面是一个简单的基于卡尔曼滤波Matlab程序示例: ```matlab % 定义系统模型 A = [1 1; 0 1]; % 状态转移矩阵 B = [0.5; 1]; % 输入矩阵 C = [1 0]; % 观测矩阵 Q = [0.01 0; 0 0.01]; % 状态噪声协方差矩阵 R = 1; % 观测噪声方差 % 初始化状态和协方差 x0 = [0; 0]; % 初始状态 P0 = [1 0; 0 1]; % 初始协方差 % 生成观测数据 T = 100; % 时间步数 u = zeros(T, 1); % 输入信号 y = zeros(T, 1); % 观测数据 x_true = zeros(2, T); % 真实状态 for t = 1:T % 更新真实状态 x_true(:, t+1) = A * x_true(:, t) + B * u(t) + sqrt(Q) * randn(2, 1); % 生成观测数据 y(t) = C * x_true(:, t+1) + sqrt(R) * randn; end % 使用卡尔曼滤波进行状态估计 x_est = zeros(2, T+1); % 估计状态 P_est = zeros(2, 2, T+1); % 估计协方差 x_est(:, 1) = x0; P_est(:, :, 1) = P0; for t = 1:T % 预测步骤 x_pred = A * x_est(:, t) + B * u(t); P_pred = A * P_est(:, :, t) * A' + Q; % 更新步骤 K = P_pred * C' / (C * P_pred * C' + R); x_est(:, t+1) = x_pred + K * (y(t) - C * x_pred); P_est(:, :, t+1) = (eye(2) - K * C) * P_pred; end % 绘制结果 figure; plot(1:T+1, x_true(1, :), 'b-', 'LineWidth', 2); hold on; plot(1:T+1, x_est(1, :), 'r--', 'LineWidth', 2); legend('真实状态', '估计状态'); xlabel('时间步数'); ylabel('状态值'); title('基于卡尔曼滤波的状态估计'); % 相关问题: 1. 什么是卡尔曼滤波? 2. 卡尔曼滤波的原理是什么? 3. 如何选择卡尔曼滤波中的噪声协方差矩阵? 4. 卡尔曼滤波在实际应用中有哪些限制? ```
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值