回忆: 通过对惯导数据执行vins_estimator/src/estimator/estimator.cpp中inputIMU函数将原始数据存放到队列accBuf(t 、acc )、gyrBuf(t、gyr)再通过fastPredictIMU得到latest_time,latest_Q,latest_P,latest_V,latest_acc_0,latest_gyr_0变量。
接下来进入processMesurements函数
processMeasurements();
1.数据流
1.1.
if ((!USE_IMU || IMUAvailable(feature.first + td)))
1.2
getIMUInterval(prevTime, curTime, accVector, gyrVector);
1.3
if(!initFirstPoseFlag)
initFirstIMUPose(accVector);
1.4
processIMU(accVector[i].first, dt, accVector[i].second, gyrVector[i].second);
存在的问题初始的惯导偏置是怎么来的,初始设置为零,后不断优化得到。 2.processimu详解:
2.1
pre_integrations[frame_count] = new IntegrationBase{acc_0, gyr_0, Bas[frame_count], Bgs[frame_count]};
2.2
pre_integrations[frame_count]->push_back(dt, linear_acceleration, angular_velocity);
2.2.1
propagate(dt, acc, gyr);—— midPointIntegration函数
* 中值积分
* 1、前一时刻状态计算当前时刻状态PVQ,其中Ba,Bg保持不变
* 2、计算当前时刻的误差Jacobian,误差协方差 todo
* @param dt历元之间时间间隔
* @param acc_0上一帧的对应的imu数组
* @param acc_1当前帧imu数据
* @param delta_p ,delta_q, delta_v上一时刻的 pvq 预积分结果,linearized_ba, linearized_bg上一时刻偏置
* @param result_预积分结果
*/
midPointIntegration(_dt, acc_0, gyr_0, _acc_1, _gyr_1, delta_p, delta_q, delta_v,
linearized_ba, linearized_bg,
result_delta_p, result_delta_q, result_delta_v,
result_linearized_ba, result_linearized_bg, 1);
2.2.1.1更新pvq
Vector3d un_acc_0 = delta_q * (_acc_0 - linearized_ba);
Vector3d un_gyr = 0.5 * (_gyr_0 + _gyr_1) - linearized_bg;
result_delta_q = delta_q * Quaterniond(1, un_gyr(0) * _dt / 2, un_gyr(1) * _dt / 2, un_gyr(2) * _dt / 2);
Vector3d un_acc_1 = result_delta_q * (_acc_1 - linearized_ba);
Vector3d un_acc = 0.5 * (un_acc_0 + un_acc_1);
result_delta_p = delta_p + delta_v * _dt + 0.5 * un_acc * _dt * _dt;
result_delta_v = delta_v + un_acc * _dt;
result_linearized_ba = linearized_ba;
result_linearized_bg = linearized_bg;
2.2.1.2更新雅克比和协方差阵
jacobian = F * jacobian;
covariance = F * covariance * F.transpose() + V * noise * V.transpose();
2.3更新绝对坐标系下的位置
int j = frame_count;
Vector3d un_acc_0 = Rs[j] * (acc_0 - Bas[j]) - g;
Vector3d un_gyr = 0.5 * (gyr_0 + angular_velocity) - Bgs[j];
Rs[j] *= Utility::deltaQ(un_gyr * dt).toRotationMatrix();
Vector3d un_acc_1 = Rs[j] * (linear_acceleration - Bas[j]) - g;
Vector3d un_acc = 0.5 * (un_acc_0 + un_acc_1);
Ps[j] += dt * Vs[j] + 0.5 * dt * dt * un_acc;
Vs[j] += dt * un_acc;
疑问?frame_count是怎样更新的还是不需要更新是滑动窗口的定值。 已解决:estimator.cpp初始化过程中,同时在两帧之间的frame_count是相同的。
if(frame_count < WINDOW_SIZE)
{
frame_count++;
int prev_frame = frame_count - 1;
Ps[frame_count] = Ps[prev_frame];
Vs[frame_count] = Vs[prev_frame];
Rs[frame_count] = Rs[prev_frame];
Bas[frame_count] = Bas[prev_frame];
Bgs[frame_count] = Bgs[prev_frame];
}
|