3、IMU原理与误差模型:加速度计与陀螺仪的工作原理、零偏、标度因数、交叉耦合误差、噪声模型(Allan方差)
好,咱们进入正题。IMU,也就是惯性测量单元,是飞控的“感觉器官”。你想想看,飞机在天上飞,GPS可能丢星,视觉可能失效,但IMU永远在实时输出数据。所以,搞懂它的原理和误差,是校准的第一步。
3.1 加速度计的工作原理
加速度计测量的是比力,不是单纯的运动加速度。说白了,它测的是物体受到的惯性力与重力的合力。我习惯用一个比喻:你坐在一辆加速的汽车里,身体被压在座椅上,那个“压感”就是加速度计在测量的东西。
常见的MEMS加速度计内部是一个微小的质量块,由硅悬臂梁支撑。当有加速度时,质量块会移动,改变电容值。通过检测电容变化,就能反推出加速度。
关键点:静止时,加速度计测到的是1g的重力加速度。所以,如果你把加速度计平放,Z轴输出应该是9.8 m/s²左右。我遇到过不少新手,看到静止时Z轴不是0就慌了,其实这是正常的。
3.2 陀螺仪的工作原理
陀螺仪测量角速度。MEMS陀螺仪用的是科里奥利效应。嗯,这个听起来有点绕,我简单解释一下:
一个质量块在高速振动,如果给它施加一个旋转,振动方向就会发生偏转。这个偏转量正比于角速度。通过检测这个偏转,就能算出转得有多快。
我个人习惯把陀螺仪想象成一个“旋转传感器”。它告诉你飞机在绕哪个轴转,转得多快。但注意,它测的是角速度,不是角度。要得到角度,得做积分。
警告:陀螺仪的积分漂移是飞控的大敌。我曾经在一个项目中,因为陀螺仪零偏没校准好,积分10分钟就漂了30度,飞机直接翻了个跟头。所以,误差模型必须搞扎实。
3.3 误差模型:零偏
零偏,也叫Bias,是IMU最核心的误差之一。理想情况下,IMU静止时输出应该是0(加速度计输出重力加速度除外)。但实际上,由于制造工艺、温度变化、应力释放等原因,输出会有一个固定的偏移。
零偏的数学表达很简单:
output = true_value + bias + noise
对于加速度计,零偏的单位是mg(毫g)。对于陀螺仪,单位是°/s或°/h。
我的经验:零偏不是一成不变的。每次上电,零偏都可能不同。所以,飞控上电后通常会做一段时间的静态采集,取平均作为本次飞行的零偏估计。这叫“上电零偏校准”。
3.4 标度因数误差
标度因数,说白了就是“比例尺”。理想情况下,输入1°/s的角速度,陀螺仪应该输出1°/s。但实际中,输出可能是0.98或1.02。这个比例偏差就是标度因数误差。
标度因数误差通常用ppm(百万分之一)或百分比表示。举个例子:
| 误差类型 | 典型值 | 影响 |
|---|---|---|
| 加速度计标度因数误差 | 0.1% ~ 1% | 导致速度积分误差 |
| 陀螺仪标度因数误差 | 0.05% ~ 0.5% | 导致姿态角积分误差 |
我记得有一次做高精度测绘无人机,标度因数误差没校准好,导致飞行轨迹偏差了2米。对于测绘来说,这误差就大了去了。
3.5 交叉耦合误差
交叉耦合,也叫轴间串扰。理想情况下,X轴的加速度只影响X轴的输出。但实际中,X轴的加速度可能会在Y轴或Z轴上产生微小输出。这就是交叉耦合。
交叉耦合误差通常用一个3x3的矩阵来描述:
[output_x] [Sxx Sxy Sxz] [input_x]
[output_y] = [Syx Syy Syz] * [input_y]
[output_z] [Szx Szy Szz] [input_z]
其中,Sxx、Syy、Szz是标度因数,Sxy、Sxz等是交叉耦合系数。理想情况下,交叉耦合系数应该为0。
避坑指南:我曾经遇到过一批IMU,交叉耦合误差特别大,达到了2%。查了半天,发现是封装应力导致的。后来通过六位置法校准,才把误差压到0.1%以下。所以,批量生产时一定要做交叉耦合校准。
3.6 噪声模型与Allan方差
噪声是IMU的固有特性。你想想看,即使IMU完全静止,输出也不是一个恒定值,而是在某个值附近随机跳动。这个跳动就是噪声。
常见的噪声类型包括:
- 白噪声:高频随机波动,功率谱密度平坦
- 随机游走:低频漂移,积分后误差会累积
- 量化噪声:ADC量化带来的误差
- 闪烁噪声:1/f噪声,低频段明显
Allan方差是分析IMU噪声的经典工具。它的做法很简单:取一段长时间的静态数据,然后按不同的时间窗口做平均,计算方差。最后画出log-log曲线。
Allan方差曲线能告诉我们:
- 曲线最低点对应的是零偏稳定性(Bias Instability)
- 斜率为-1/2的部分对应白噪声(角度随机游走)
- 斜率为+1/2的部分对应速率随机游走
- 斜率为+1的部分对应量化噪声
实用技巧:我建议每个飞控工程师都学会看Allan方差图。它就像IMU的“体检报告”。有一次,我发现一款新IMU的Allan方差曲线异常,查了半天发现是电源纹波太大。换了LDO后,噪声降了一个数量级。
3.7 误差补偿的工程实践
理论讲完了,咱们聊聊实际怎么做。在飞控固件中,误差补偿通常放在传感器数据读取之后,姿态解算之前。
一个典型的补偿流程:
// 伪代码示例
void compensate_imu(imu_data_t *raw, imu_data_t *compensated) {
// 1. 减去零偏
compensated->accel.x = raw->accel.x - bias.accel.x;
compensated->accel.y = raw->accel.y - bias.accel.y;
compensated->accel.z = raw->accel.z - bias.accel.z;
compensated->gyro.x = raw->gyro.x - bias.gyro.x;
compensated->gyro.y = raw->gyro.y - bias.gyro.y;
compensated->gyro.z = raw->gyro.z - bias.gyro.z;
// 2. 标度因数与交叉耦合补偿(矩阵乘法)
// 这里用3x3矩阵处理
float accel_comp[3];
matrix_multiply(scale_matrix, compensated->accel, accel_comp);
compensated->accel.x = accel_comp[0];
compensated->accel.y = accel_comp[1];
compensated->accel.z = accel_comp[2];
// 3. 温度补偿(如果有温度模型)
compensated->gyro.x += temp_coeff.gyro.x * (temp - ref_temp);
// ...
}
注意:补偿顺序很重要。我习惯先减零偏,再做标度因数补偿。如果顺序反了,误差会放大。另外,温度补偿最好放在最后,因为温度变化会影响零偏和标度因数。
好了,IMU的原理和误差模型就讲到这里。下一章咱们会聊具体的校准方法——六位置法和速率法。到时候我会分享一些实操中的小技巧,比如怎么判断校准数据是否有效,怎么处理异常值等等。