// 最佳线性滤波理论起源于40年代美国科学家Wiener和前苏联科学家Kолмогоров等人的研究工作,
// 后人统称为维纳滤波理论。从理论上说,维纳滤波的最大缺点是必须用到无限过去的数据,不适用于实时处理。
// 为了克服这一缺点,60年代Kalman把状态空间模型引入滤波理论,并导出了一套递推估计算法,
// 后人称之为卡尔曼滤波理论。卡尔曼滤波是以最小均方误差为估计的最佳准则,来寻求一套递推估计的算法,
// 其基本思想是:采用信号与噪声的状态空间模型,利用前一时刻地估计值和现时刻的观测值来更新对状态变量的估计,
// 求出现时刻的估计值。它适合于实时处理和计算机运算。
//
//
//
//现设线性时变系统的离散状态防城和观测方程为:
//
//
//
//X(k) = F(k,k-1)·X(k-1)+T(k,k-1)·U(k-1)
//
//
//
//Y(k) = H(k)·X(k)+N(k)
//
//
//
//其中
//
//
//
//X(k)和Y(k)分别是k时刻的状态矢量和观测矢量
//
//
//
//F(k,k-1)为状态转移矩阵
//
//
//
//U(k)为k时刻动态噪声
//
//
//
//T(k,k-1)为系统控制矩阵
//
//
//
//H(k)为k时刻观测矩阵
//
//
//
//N(k)为k时刻观测噪声
//
//
//
//则卡尔曼滤波的算法流程为:
//
//
//
//
//
//预估计X(k)^= F(k,k-1)·X(k-1)
//
//计算预估计协方差矩阵
//C(k)^=F(k,k-1)×C(k)×F(k,k-1)'+T(k,k-1)×Q(k)×T(k,k-1)'
//Q(k) = U(k)×U(k)'
//
//计算卡尔曼增益矩阵
//K(k) = C(k)^×H(k)'×[H(k)×C(k)^×H(k)'+R(k)]^(-1)
//R(k) = N(k)×N(k)'
//
//更新估计
//X(k)~=X(k)^+K(k)×[Y(k)-H(k)×X(k)^]
//
//计算更新后估计协防差矩阵
//C(k)~ = [I-K(k)×H(k)]×C(k)^×[I-K(k)×H(k)]'+K(k)×R(k)×K(k)'
//
//X(k+1) = X(k)~
//C(k+1) = C(k)~
//重复以上步骤
//**************************************************************
//C语言代码:
//************************************************************
#include "stdlib.h"
//#include "rinv.c"
//int n,m,k;
//double f[100],q[100],r[100],h[100],y[100],x[100],p[100],g[100];
int lman(int n,int m,int k,double *f,double *q,double *r,double *h,double *y,double *x,double *p,double *g);
int main()
{
return 0;
}
int lman(int n,int m,int k,double *f,double *q,double *r,double *h,double *y,double *x,double *p,double *g)
{
int i,j,kk,ii,l,jj,js;
double *e,*a,*b;
e=malloc(m*m*sizeof(double));
l=m;
if (l
l=n;
a=malloc(l*l*sizeof(double));
b=malloc(l*l*sizeof(double));
for (i=0; i<=n-1; i++)
for (j=0; j<=n-1; j++)
{
ii=i*l+j; a[ii]=0.0;
for (kk=0; kk<=n-1; kk++)
a[ii]=a[ii]+p[i*n+kk]*f[j*n+kk];
}
for (i=0; i<=n-1; i++)
for (j=0; j<=n-1; j++)
{
ii=i*n+j; p[ii]=q[ii];
for (kk=0; kk<=n-1; kk++)
p[ii]=p[ii]+f[i*n+kk]*a[kk*l+j];
}
for (ii=2; ii<=k; ii++)
{
for (i=0; i<=n-1; i++)
for (j=0; j<=m-1; j++)
{
jj=i*l+j; a[jj]=0.0;
for (kk=0; kk<=n-1; kk++)
a[jj]=a[jj]+p[i*n+kk]*h[j*n+kk];
}
for (i=0; i<=m-1; i++)
for (j=0; j<=m-1; j++)
{
jj=i*m+j; e[jj]=r[jj];
for (kk=0; kk<=n-1; kk++)
e[jj]=e[jj]+h[i*n+kk]*a[kk*l+j];
}
js=rinv(e,m);
if (js==0)
{
free(e);
free(a);
free(b);
return(js);
}
for (i=0; i<=n-1; i++)
for (j=0; j<=m-1; j++)
{
jj=i*m+j; g[jj]=0.0;
for (kk=0; kk<=m-1; kk++)
g[jj]=g[jj]+a[i*l+kk]*e[j*m+kk];
}
for (i=0; i<=n-1; i++)
{
jj=(ii-1)*n+i; x[jj]=0.0;
for (j=0; j<=n-1; j++)
x[jj]=x[jj]+f[i*n+j]*x[(ii-2)*n+j];
}
for (i=0; i<=m-1; i++)
{
jj=i*l; b[jj]=y[(ii-1)*m+i];
for (j=0; j<=n-1; j++)
b[jj]=b[jj]-h[i*n+j]*x[(ii-1)*n+j];
}
for (i=0; i<=n-1; i++)
{
jj=(ii-1)*n+i;
for (j=0; j<=m-1; j++)
x[jj]=x[jj]+g[i*m+j]*b[j*l];
}
if (ii
{
for (i=0; i<=n-1; i++)
for (j=0; j<=n-1; j++)
{
jj=i*l+j; a[jj]=0.0;
for (kk=0; kk<=m-1; kk++)
a[jj]=a[jj]-g[i*m+kk]*h[kk*n+j];
if (i==j) a[jj]=1.0+a[jj];
}
for (i=0; i<=n-1; i++)
for (j=0; j<=n-1; j++)
{
jj=i*l+j; b[jj]=0.0;
for (kk=0; kk<=n-1; kk++)
b[jj]=b[jj]+a[i*l+kk]*p[kk*n+j];
}
for (i=0; i<=n-1; i++)
for (j=0; j<=n-1; j++)
{
jj=i*l+j; a[jj]=0.0;
for (kk=0; kk<=n-1; kk++)
a[jj]=a[jj]+b[i*l+kk]*f[j*n+kk];
}
for (i=0; i<=n-1; i++)
for (j=0; j<=n-1; j++)
{
jj=i*n+j; p[jj]=q[jj];
for (kk=0; kk<=n-1; kk++)
p[jj]=p[jj]+f[i*n+kk]*a[j*l+kk];
}
}
}
free(e);
free(a);
free(b);
return(js);
}
一键复制
编辑
Web IDE
原始数据
按行查看
历史