捷联惯导算法(一)程序简单实现


前言

文中算法公式摘自《捷联惯导算法与组合导航原理》(严恭敏、翁浚 编著)、《惯性导航》(秦永元 编著),其他理解仅代表个人观点。本文对捷联惯导算法使用Matlab进行简单实现,不包含算法理解。


一、捷联惯导算法实现内容

已知初始位置和加速度计比力、陀螺仪角增量(即很短测量时间段内各个轴向速度和角度变化)推算出整个过程中姿态(俯仰角 、横滚角 、航向角 )、速度、位置(纬度 、经度 、高度 )信息。

二、用到的参数

三、捷联惯导更新算法

1.姿态更新算法

1.1、姿态更新算法中用到的是姿态更新矩阵进行更新,首先将姿态角转化为姿态更新矩阵

程序实现

function [ Mat ] = Att2Mat_sins( att )
%姿态角转化为姿态矩阵
C_1=[ 1       0            0;
      0  cos(att(1))   sin(att(1));
      0  -sin(att(1))  cos(att(1))];
C_2=[cos(att(2))   0  -sin(att(2));
            0      1        0;
     sin(att(2))   0  cos(att(2))];
C_3=[cos(att(3)) -sin(att(3)) 0;
     sin(att(3)) cos(att(3))  0;
           0          0      1];
Mat=(C_2*C_1*C_3)';
end

1.2算法程序

用到的子函数

function [ MRV ] = MRV( phi )
n=length(phi);
phi_fan=Fan(phi);
phi_2=norm(phi,2);
MRV=eye(n)+sin(phi_2)/phi_2*phi_fan+(1-cos(phi_2))/phi_2^2*phi_fan^2;
end
function [ phi_fan ] = Fan( phi )
% 反对称阵
phi_fan=[0 -phi(3) phi(2);phi(3) 0 -phi(1);-phi(2) phi(1) 0];
end

1.3最后将姿态矩阵转化为姿态角

在Matlab中可以直接进行转化,不需要判断,程序如下:

function [ att ] = Mat2Att_sins( Mat )
%姿态矩阵转化为姿态角,转化结果单位为度
att=[asind(Mat(3,2)) rad2deg(atan2(-Mat(3,1),Mat(3,3))) rad2deg(atan2(Mat(1,2),Mat(2,2)))];
end

1.4完整姿态更新程序

%姿态更新
C_bn1=Att2Mat_sins(avp1(1:3));%姿态角转化为姿态矩阵
wien_1=[0 wie*cos(avp1(7)) wie*sin(avp1(7))]';
wenn_1=[-avp1(5)/(R_M_1+avp1(9)) avp1(4)/(R_N_1+avp1(9)) tan(avp1(7))*avp1(4)/(R_N_1+avp1(9))]';
winn_1=wien_1+wenn_1;
C_nn=MRV(Tm*winn_1)';
phi_ibb=(delta_theta1+delta_theta2)+2/3*cross(delta_theta1,delta_theta2);
C_bb=MRV(phi_ibb);
C_bn2=C_nn*C_bn1*C_bb;%姿态更新
avp2(1:3)=Mat2Att_sins(C_bn2);%姿态矩阵转化为姿态角

2.速度更新算法

数据外推程序

function [y10 ] = waitui( y1,y0 )
%数据外推
y10=(3*y1-y0)/2;
end

第一次解算速度更新算法:

%速度更新
deltav_rot=1/2*cross((delta_theta1+delta_theta2),(delta_v1+delta_v2));
deltav_scul=2/3*(cross(delta_theta1,delta_v2)+cross(delta_v1,delta_theta2));
deltav_sfm=(eye(3)-Tm/2*Fan(winn_1))*C_bn1*(delta_v1+delta_v2+deltav_rot+deltav_scul)';
    g=g0*(1+5.27094e-3*sin(avp1(7))^2+2.32718e-5*sin(avp1(7))^4)-3.086e-6*avp1(9);
    gn=[0 0 -g];
deltav_cor=(gn-cross((2*wien_1+wenn_1),avp1(4:6)))*Tm;
avp2(4:6)=avp1(4:6)+deltav_sfm'+deltav_cor;%速度更新

后续解算使用外推数据更新算法

%外推数据速度更新
    wien_0=[0 wie*cos(avp0(7)) wie*sin(avp0(7))]';
    wenn_0=[-avp0(5)/(R_M_0+avp0(9)) avp0(4)/(R_N_0+avp0(9)) tan(avp0(7))*avp0(4)/(R_N_0+avp0(9))]';
    wien_10=waitui(wien_1,wien_0);
    wenn_10=waitui(wenn_1,wenn_0);
    winn_10=wien_10+wenn_10;%x_10代表外推数据
deltav_rot=1/2*cross((delta_theta1+delta_theta2),(delta_v1+delta_v2));
deltav_scul=2/3*(cross(delta_theta1,delta_v2)+cross(delta_v1,delta_theta2));
deltav_sfm=(eye(3)-Tm/2*Fan(winn_10))*C_bn1*(delta_v1+delta_v2+deltav_rot+deltav_scul)';
    g_1=g0*(1+5.27094e-3*sin(avp1(7))^2+2.32718e-5*sin(avp1(7))^4)-3.086e-6*avp1(9);
    g_0=g0*(1+5.27094e-3*sin(avp0(7))^2+2.32718e-5*sin(avp0(7))^4)-3.086e-6*avp0(9);
    gn=[0 0 -waitui(g_1,g_0)];
deltav_cor=(gn-cross((2*wien_10+wenn_10),waitui(avp1(4:6),avp0(4:6))))*Tm;
avp2(4:6)=avp1(4:6)+deltav_sfm'+deltav_cor;%速度更新

3.位置更新算法

对矩阵可以使用整体外推法,也可以对矩阵中的元素外推,再构造矩阵,程序中使用整体外推法。
第一次解算位置更新程序

%位置更新
Mpv=[0 1/(R_M_1+avp1(9)) 0; sec(avp1(7))/(R_N_1+avp1(9)) 0 0;0 0 1];
avp2(7:9)=avp1(7:9)+(Mpv*(avp1(4:6)+avp2(4:6))'*Tm/2)';%位置更新

后续使用外推解算位置更新程序

%外推数据位置更新
    Mpv_1=[0 1/(R_M_1+avp1(9)) 0; sec(avp1(7))/(R_N_1+avp1(9)) 0 0;0 0 1];
    Mpv_0=[0 1/(R_M_0+avp0(9)) 0; sec(avp0(7))/(R_N_0+avp0(9)) 0 0;0 0 1];
Mpv=waitui(Mpv_1,Mpv_0);%使用对矩阵Mpv整体外推法
avp2(7:9)=avp1(7:9)+(Mpv*(avp1(4:6)+avp2(4:6))'*Tm/2)';%位置更新

附录(完整程序)

程序清单:
1、主函数
2、主要子函数(2个):第一次解算函数、后续使用外推数据解算函数
3、其他子函数(5个):姿态角转化为姿态矩阵函数、姿态矩阵转化为姿态角函数、等效旋转矢量函数、反对称矩阵函数、数据外推函数

主函数

clc
clear
load imu.mat;%1-3列:陀螺仪xyz轴数据(单位:弧度)、4-6列:加速度计xyz轴数据(单位m/s)、第7列为时间
ins_data=zeros(length(imu)/2+1,10);%俯仰、横滚、航向角、xyz轴速度、纬度、经度、高度、时间,角度单位为度
ins_data(1,:)=[0 0 -10*180/pi 0 0 0 34 106 380 0];%初始值,最后一列为时间
ins_data(2,:)=sins(ins_data(1,:),imu(1:2,:));%第一次解算不使用外推
for k=4:2:length(imu)
    %使用二子样算法,每次输入两次的惯性器件采样数据和前两时刻的avp数据
    ins_data(k/2+1,:)=sins_waitui(ins_data(k/2,:),ins_data(k/2-1,:),imu(k-1:k,:));
end

第一次解算函数

function [ avp2 ] = sins( avp1,imu )
%imu数据
Tm=2*(imu(2,7)-imu(1,7));
delta_theta1=imu(1,1:3);delta_theta2=imu(2,1:3);
delta_v1=imu(1,4:6);delta_v2=imu(2,4:6);
%参数
Re=6378254;%单位:m
f=1/298.3;
wie=7.292115e-5;%单位:rad/s
g0=9.780325333434361;%单位;m/s^2
e2=2*f-f^2;
R_N_1=Re/sqrt(1-e2*sin(avp1(7)));
R_M_1=R_N_1*(1-e2)/(1-e2*sin(avp1(7))^2);
avp1([1:3 7 8])=deg2rad(avp1([1:3 7 8]));%将所有角度转化为弧度,结算中用到的角度都是弧度单位

%姿态更新
C_bn1=Att2Mat_sins(avp1(1:3));%姿态角转化为姿态矩阵
wien_1=[0 wie*cos(avp1(7)) wie*sin(avp1(7))]';
wenn_1=[-avp1(5)/(R_M_1+avp1(9)) avp1(4)/(R_N_1+avp1(9)) tan(avp1(7))*avp1(4)/(R_N_1+avp1(9))]';
winn_1=wien_1+wenn_1;
C_nn=MRV(Tm*winn_1)';
phi_ibb=(delta_theta1+delta_theta2)+2/3*cross(delta_theta1,delta_theta2);
C_bb=MRV(phi_ibb);
C_bn2=C_nn*C_bn1*C_bb;%姿态更新
avp2(1:3)=Mat2Att_sins(C_bn2);%姿态矩阵转化为姿态角

%速度更新
deltav_rot=1/2*cross((delta_theta1+delta_theta2),(delta_v1+delta_v2));
deltav_scul=2/3*(cross(delta_theta1,delta_v2)+cross(delta_v1,delta_theta2));
deltav_sfm=(eye(3)-Tm/2*Fan(winn_1))*C_bn1*(delta_v1+delta_v2+deltav_rot+deltav_scul)';
    g=g0*(1+5.27094e-3*sin(avp1(7))^2+2.32718e-5*sin(avp1(7))^4)-3.086e-6*avp1(9);
    gn=[0 0 -g];
deltav_cor=(gn-cross((2*wien_1+wenn_1),avp1(4:6)))*Tm;
avp2(4:6)=avp1(4:6)+deltav_sfm'+deltav_cor;%速度更新

%位置更新
Mpv=[0 1/(R_M_1+avp1(9)) 0; sec(avp1(7))/(R_N_1+avp1(9)) 0 0;0 0 1];
avp2(7:9)=avp1(7:9)+(Mpv*(avp1(4:6)+avp2(4:6))'*Tm/2)';%位置更新
avp2(7:8)=rad2deg(avp2(7:8));%将角度坐标转化为弧度

avp2(10)=imu(2,7);%时间
end

后续使用外推数据解算函数

function [ avp2 ] = sins_waitui( avp1,avp0,imu )
%imu数据
Tm=2*(imu(2,7)-imu(1,7));
delta_theta1=imu(1,1:3);delta_theta2=imu(2,1:3);
delta_v1=imu(1,4:6);delta_v2=imu(2,4:6);
%参数
Re=6378254;%单位:m
f=1/298.3;
wie=7.292115e-5;%单位:rad/s
g0=9.780325333434361;%单位;m/s^2
e2=2*f-f^2;
R_N_0=Re/sqrt(1-e2*sin(avp0(7)));
R_M_0=R_N_0*(1-e2)/(1-e2*sin(avp0(7))^2);
R_N_1=Re/sqrt(1-e2*sin(avp1(7)));
R_M_1=R_N_1*(1-e2)/(1-e2*sin(avp1(7))^2);
avp1([1:3 7 8])=deg2rad(avp1([1:3 7 8]));
avp0([1:3 7 8])=deg2rad(avp0([1:3 7 8]));

%姿态更新
C_bn1=Att2Mat_sins(avp1(1:3));%姿态角转化为姿态矩阵
wien_1=[0 wie*cos(avp1(7)) wie*sin(avp1(7))]';
wenn_1=[-avp1(5)/(R_M_1+avp1(9)) avp1(4)/(R_N_1+avp1(9)) tan(avp1(7))*avp1(4)/(R_N_1+avp1(9))]';
winn_1=wien_1+wenn_1;
C_nn=MRV(Tm*winn_1)';
phi_ibb=(delta_theta1+delta_theta2)+2/3*cross(delta_theta1,delta_theta2);
C_bb=MRV(phi_ibb);
C_bn2=C_nn*C_bn1*C_bb;%姿态更新
avp2(1:3)=Mat2Att_sins(C_bn2);%姿态矩阵转化为姿态角

%速度更新
    wien_0=[0 wie*cos(avp0(7)) wie*sin(avp0(7))]';
    wenn_0=[-avp0(5)/(R_M_0+avp0(9)) avp0(4)/(R_N_0+avp0(9)) tan(avp0(7))*avp0(4)/(R_N_0+avp0(9))]';
    wien_10=waitui(wien_1,wien_0);
    wenn_10=waitui(wenn_1,wenn_0);
    winn_10=wien_10+wenn_10;%x_10代表外推数据
deltav_rot=1/2*cross((delta_theta1+delta_theta2),(delta_v1+delta_v2));
deltav_scul=2/3*(cross(delta_theta1,delta_v2)+cross(delta_v1,delta_theta2));
deltav_sfm=(eye(3)-Tm/2*Fan(winn_10))*C_bn1*(delta_v1+delta_v2+deltav_rot+deltav_scul)';
    g_1=g0*(1+5.27094e-3*sin(avp1(7))^2+2.32718e-5*sin(avp1(7))^4)-3.086e-6*avp1(9);
    g_0=g0*(1+5.27094e-3*sin(avp0(7))^2+2.32718e-5*sin(avp0(7))^4)-3.086e-6*avp0(9);
    gn=[0 0 -waitui(g_1,g_0)];
deltav_cor=(gn-cross((2*wien_10+wenn_10),waitui(avp1(4:6),avp0(4:6))))*Tm;
avp2(4:6)=avp1(4:6)+deltav_sfm'+deltav_cor;%速度更新

%位置更新
    Mpv_1=[0 1/(R_M_1+avp1(9)) 0; sec(avp1(7))/(R_N_1+avp1(9)) 0 0;0 0 1];
    Mpv_0=[0 1/(R_M_0+avp0(9)) 0; sec(avp0(7))/(R_N_0+avp0(9)) 0 0;0 0 1];
Mpv=waitui(Mpv_1,Mpv_0);%使用对矩阵Mpv整体外推法
avp2(7:9)=avp1(7:9)+(Mpv*(avp1(4:6)+avp2(4:6))'*Tm/2)';%位置更新
avp2(7:8)=rad2deg(avp2(7:8));%将角度坐标转化为弧度

avp2(10)=imu(2,7);%时间
end

姿态角转化为姿态矩阵函数

function [ Mat ] = Att2Mat_sins( att )
%姿态角转化为姿态矩阵
C_1=[ 1       0            0;
      0  cos(att(1))   sin(att(1));
      0  -sin(att(1))  cos(att(1))];
C_2=[cos(att(2))   0  -sin(att(2));
            0      1        0;
     sin(att(2))   0  cos(att(2))];
C_3=[cos(att(3)) -sin(att(3)) 0;
     sin(att(3)) cos(att(3))  0;
           0          0      1];
Mat=(C_2*C_1*C_3)';
end

姿态矩阵转化为姿态角函数

function [ att ] = Mat2Att_sins( Mat )
%姿态矩阵转化为姿态角,转化结果单位为度
att=[asind(Mat(3,2)) rad2deg(atan2(-Mat(3,1),Mat(3,3))) rad2deg(atan2(Mat(1,2),Mat(2,2)))];
end

等效旋转矢量函数

function [ MRV ] = MRV( phi )
n=length(phi);
phi_fan=Fan(phi);
phi_2=norm(phi,2);
MRV=eye(n)+sin(phi_2)/phi_2*phi_fan+(1-cos(phi_2))/phi_2^2*phi_fan^2;
end

反对称矩阵函数

function [ phi_fan ] = Fan( phi )
% 反对称阵
phi_fan=[0 -phi(3) phi(2);phi(3) 0 -phi(1);-phi(2) phi(1) 0];
end

数据外推函数

function [y10 ] = waitui( y1,y0 )
%数据外推
y10=(3*y1-y0)/2;
end
评论 16
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值