从卡尔曼滤波到信息滤波:多传感器融合的状态估计新思路
卡尔曼滤波这套东西做过状态估计的人都能背出那五个方程但真正在多传感器融合的工程现场泡过几年之后你会发现标准形式在某些场景下会变得特别别扭。信息滤波Information Filter就是冲着这种别扭来的——它把高斯分布从均值加协方差的写法换成信息向量加信息矩阵的写法换完之后观测更新变成了一句加法多传感器往同一个状态估计里塞观测时几乎不需要任何协调。代价也明摆着预测步骤从一行公式变成一个矩阵求逆。这笔买卖划不划算取决于你的系统是观测密集还是预测密集是单机跑还是分布式跑。下面我把整套推导从头捋一遍会讲清楚每一步为什么要这么走、哪些地方容易卡壳以及用 numpy 复现时我自己踩过的坑。1. 为什么值得把卡尔曼滤波换个写法1.1 从一次多传感器融合的麻烦说起假设你手上有一台移动平台上面挂着激光雷达、轮式里程计、IMU还有一个视觉模块。每个传感器都有自己的观测模型和噪声特性你需要把它们的信息融进同一个状态估计里。用标准卡尔曼滤波做这件事流程是这样的先做一次预测得到先验均值和先验协方差然后拿第一个传感器的观测做一次更新得到后验再拿第二个传感器的观测对刚才的后验再做一次更新得到新的后验第三个、第四个依此类推。这个串行流程本身没错数学上完全等价于把四个观测拼成一个大观测向量一次性更新。问题出在工程实现上。每一次更新都要计算卡尔曼增益而计算增益绕不开对创新协方差矩阵求逆那个矩阵的维度等于该传感器的观测维度。四个传感器就要做四次求逆而且这四次更新必须严格按顺序执行前一个的结果是后一个的输入。如果你想把这四个传感器的处理拆到四个进程或者四块板子上并行跑就会非常难受因为下游必须等上游算完。更麻烦的是如果某个传感器临时掉线整个更新链的中间态需要重新组织代码里到处是分支判断。信息滤波解决的正是这个结构性问题。在信息形式下每个传感器的贡献是一份独立的加项把它们加起来就完事加法的顺序无所谓谁先算完谁先加掉线了不加就行不需要任何补偿逻辑。这个性质在分布式估计、传感器网络、多机器人协同定位里是决定性的。1.2 信息矩阵与协方差矩阵的对偶关系要理解信息滤波先要接受一个事实描述一个高斯分布均值和协方差不是唯一的选择。协方差矩阵 Σ 描述的是不确定性有多大对角线元素越大表示越不确定。而它的逆矩阵 Λ Σ⁻¹ 描述的是确定性有多强数值越大表示该方向上的约束越紧。后者就是所谓的信息矩阵有些文献也叫精度矩阵。这种对偶不只体现在符号上它对应着两种完全不同的物理直觉。协方差视角下你关心的是误差的散布范围一个很大的 Σ 意味着你对状态几乎一无所知。信息视角下你关心的是各个方向被约束得有多死Λ 的某个特征值很大说明在这个特征向量方向上你有非常硬的证据。举个生活化的例子协方差像是地图上画的一个模糊圈圈越大越不确定信息矩阵像是往这个圈上钉的钉子钉子越多、钉得越深圈就被压缩得越小。观测更新在协方差视角下是缩小模糊圈在信息视角下就是往圈上钉钉子而钉钉子这个动作天然是可叠加的。理解了这一层后面观测更新为什么是加法就顺理成章了——每来一个观测无非是多钉一颗钉子钉子之间互不干扰总效果就是把各自的贡献加起来。1.3 什么场景该果断换到信息形式不是所有问题都适合用信息滤波。我自己的判断标准大致是这样几条。如果你的观测更新频率远高于预测频率比如一个静止的传感器网络每隔几毫秒上报一次数据而系统状态本身变化很慢那么更新便宜、预测贵的特性就非常划算。如果你需要把估计任务分散到多个计算单元上或者需要支持任意传感器的即插即用那基本没有别的选择。如果你的观测数量非常大但每个观测维度很低比如几千个测距基站各给一个标量距离信息形式的优势会被放大到极致因为每个基站贡献的是一个秩一矩阵的加法。反过来如果你的系统是预测密集型比如高频率的惯性递推观测偶尔才来一次那标准卡尔曼形式明显更省算力。另外如果你的状态维度远大于观测维度信息矩阵会变成一个巨大的稠密矩阵而协方差形式在观测少的时候反而更容易保持稀疏结构这时候也不该硬上信息滤波。2. 高斯分布的信息形式从指数配方说起2.1 标准形式到信息形式的等价改写多变量高斯分布的标准写法是$$ p(x) (2\pi)^{-n/2} |\Sigma|^{-1/2} \exp\left(-\frac{1}{2}(x-\mu)^T \Sigma^{-1} (x-\mu)\right) $$现在做两件事令 Λ Σ⁻¹令 η Σ⁻¹μ。把指数里的二次型展开$$ -\frac{1}{2}(x-\mu)^T \Lambda (x-\mu) -\frac{1}{2}x^T\Lambda x x^T \Lambda \mu - \frac{1}{2}\mu^T \Lambda \mu $$最后那一项与 x 无关可以并进归一化常数里。注意 x^TΛμ 里的 Λμ 正好就是 η。于是整个分布可以重写成$$ p(x) \propto \exp\left(-\frac{1}{2}x^T\Lambda x x^T\eta\right) $$这就是信息形式。它看起来只是换了个写法但结构上的变化很关键指数项里 x 的二次项系数是 Λ一次项系数是 η两者完全解耦没有任何需要求逆的操作。归一化常数虽然涉及 |Σ| 的行列式但在做贝叶斯更新时我们往往只关心后验的均值和协方差归一化常数可以最后统一算很多时候甚至不需要算。注意信息向量 η 不是状态的均值。均值要从 μ Λ⁻¹η 反解出来。这一点特别容易搞混我在第一次读论文时就因为这个在代码里写错过一次症状是滤波器看起来能收敛但始终有固定偏差。2.2 信息矩阵的物理含义与 Fisher 信息的关系信息矩阵这个名字不是随便起的。在线性高斯模型下Λ 恰好等于状态的对数似然函数在真值处的负 Hessian也就是 Fisher 信息矩阵。这意味着 Λ 的每个特征值都对应一个方向上信息量的大小特征值越大该方向上参数估计的方差下界越小。这个联系带来两个实际好处。第一你可以用信息矩阵的行列式或者迹来衡量当前估计的质量这个量在传感器调度和自适应采样里很常用。第二当多个独立观测源作用在同一个状态上时总 Fisher 信息是各源 Fisher 信息之和这正是观测更新可加性的统计学根源。换句话说观测更新的加法不是巧合而是 Fisher 信息的可加性在起作用。还有一个容易被忽略的细节信息矩阵在加法下的可加性只对独立观测成立。如果两个传感器的噪声相关比如它们共享同一个时钟误差或者同一个标定偏差那么直接相加会低估后验不确定性。这时候要么显式建模互协方差要么先把相关部分做去相关处理。我在一个多相机系统里遇到过这个问题两个相机共用一个机械支架振动引起的观测噪声高度相关直接相加导致估计的置信区间比实际窄了将近一半后来加了互协方差项才修好。3. 观测更新推导为什么它能变成一步加法3.1 贝叶斯后验的指数合并设先验是 p(x) ∝ exp(-½ x^TΛx x^Tη)观测模型是线性的 z Hx v其中 v 服从均值为零、协方差为 R 的高斯分布。那么似然函数是$$ p(z|x) \propto \exp\left(-\frac{1}{2}(z-Hx)^T R^{-1}(z-Hx)\right) $$把似然的指数项展开$$ -\frac{1}{2}(z-Hx)^T R^{-1}(z-Hx) -\frac{1}{2}x^T H^T R^{-1} H x x^T H^T R^{-1} z - \frac{1}{2}z^T R^{-1} z $$最后一项不含 x并进常数。贝叶斯公式告诉我们后验正比于先验乘似然两个指数函数相乘就是指数相加把所有含 x 的项加起来$$ -\frac{1}{2}x^T\left(\Lambda H^T R^{-1} H\right)x x^T\left(\eta H^T R^{-1} z\right) $$对照信息形式的标准结构直接读出后验参数$$ \Lambda_{post} \Lambda H^T R^{-1} H, \qquad \eta_{post} \eta H^T R^{-1} z $$推导到这里就完了。整个过程没有出现任何矩阵求逆唯一需要求逆的是 R那是观测噪声协方差维度等于观测维度而且通常在离线阶段就能算好。3.2 每一步为什么成立配方与二次型合并上面这段推导看着简单但有两个地方值得展开说清楚因为它们是理解后续所有性质的基础。第一处是指数相乘等于指数相加。这看起来是废话但在贝叶斯框架里它意味着先验和似然在对数域上线性叠加。如果你把对数后验写出来会发现它是一个关于 x 的二次函数而二次函数的系数直接就是信息矩阵。这解释了为什么信息滤波在观测更新上如此简洁对数域上的叠加操作对应到信息参数上就是向量加法天然没有耦合。第二处是二次型的合并。许多人在第一次推的时候会担心先验的二次型是以 x-μ 为中心展开的似然的二次型是以 z 为中心展开的两者中心不一样合并的时候会不会出问题。答案是不会有问题因为任意二次型都可以通过配方写成标准中心 常数的形式。常数项在归一化时被吸收真正决定后验形状的只有二次项系数和一次项系数而这两者正是 Λ 和 η。你可以自己拿一维情形手动展开一遍一维情况下 P 是一个标量信息矩阵就是它的倒数写完你会发现后验方差等于两个方差倒数之和再取倒数这正是并联电阻的公式非常直观。3.3 多源观测的顺序无关性与并行融合假设现在有两个独立观测观测矩阵分别是 H₁、H₂噪声协方差 R₁、R₂观测值 z₁、z₂。按照上面的结论一次全融的总信息是$$ \Lambda \Lambda_{prior} H_1^T R_1^{-1} H_1 H_2^T R_2^{-1} H_2 $$$$ \eta \eta_{prior} H_1^T R_1^{-1} z_1 H_2^T R_2^{-1} z_2 $$如果先融 z₁ 再融 z₂中间态是 Λ H₁ᵀR₁⁻¹H₁再往上加第二项结果完全相同。因为矩阵加法满足交换律和结合律顺序完全不影响最终结果。这个性质在工程上的价值远大于它看起来的样子。它意味着你可以为每个观测源预先算好它贡献的信息增量存成一个固定结构需要的时候直接加。在分布式系统里每个观测节点只需要把 HᵀR⁻¹H 和 HR⁻¹z 这两个小矩阵通过通信链路发到融合中心融合中心做加法即可不需要知道其他节点的任何状态。更进一步如果每个节点都持有一份全局信息矩阵的副本每个节点只需要广播自己那一份增量所有节点都能独立地得到相同的融合结果这就是所谓的分布式信息滤波。代价也要说清楚。虽然更新便宜了但你要维护的是 Λ 和 η这两个量本身不是最终想要的输出。如果你需要均值还得做一次 Λ⁻¹η 的反解那次求逆跑不掉。如果你需要协方差对角元来做置信区间也要求逆。所以信息滤波省的是更新步骤里的求逆不是所有求逆这一点在评估整体算力时要算清楚。4. 预测步骤推导麻烦都堆在这里4.1 从协方差传播公式反推预测步骤在标准卡尔曼里很轻一句话就写完了先验均值往前推一步先验协方差做一次相似变换再加过程噪声。信息形式下要麻烦得多因为加在这里变成了需要求逆的操作。设系统演化是 x Ax Bu ww 服从均值为零、协方差为 Q 的高斯分布。在矩形式下$$ \mu A\mu Bu, \qquad \Sigma A\Sigma A^T Q $$注意 x 的分布仍然是高斯的条件是从旧状态出发的线性变换加上独立高斯噪声。要求它的信息形式就得把 Σ 求逆$$ \Lambda (A\Sigma A^T Q)^{-1} $$因为 Σ Λ⁻¹所以$$ \Lambda (A\Lambda^{-1}A^T Q)^{-1} $$旋转到信息视角这一步需要做一次 Λ 的求逆得到 Σ再做一次 AΣAᵀQ 的求逆得到 Λ。两个 n×n 求逆n 是状态维度。如果用四元数表示姿态n 可能是十五维甚至更高两次求逆的开销就相当可观了。信息向量的更新是$$ \eta \Lambda \mu \Lambda (A\Lambda^{-1}\eta Bu) $$这里又出现了一次 Λ⁻¹。也就是说预测步骤里一共需要两次求逆而且都必须做没法绕开。这是信息滤波最核心的取舍。观测更新是一步加法预测更新是两个矩阵求逆。你的系统如果是观测多、预测少比如低频率状态演化的静态传感器阵列收益极大如果是预测多、观测少比如高频惯性递推就要慎重。4.2 用矩阵求逆引理把求逆维度压下来上面那个 (AΛ⁻¹AᵀQ)⁻¹ 直接求逆是 n×n 的如果 Q 可逆我们可以用 Woodbury 恒等式把它改写成一个不需要求 Λ⁻¹ 的形式。Woodbury 恒等式的形式是$$ (Q A\Sigma A^T)^{-1} Q^{-1} - Q^{-1}A(\Sigma^{-1} A^T Q^{-1} A)^{-1}A^T Q^{-1} $$代入 Σ⁻¹ Λ 得到$$ \Lambda Q^{-1} - Q^{-1}A(\Lambda A^T Q^{-1} A)^{-1}A^T Q^{-1} $$这个式子的好处是它只需要求一次 (Λ AQ⁻¹A) 的逆而且不再显式构造 Σ。如果你在预测的同时还维护着 Λ那么这个量可以直接用现成的 Λ 计算。如果 Q 本身是分块对角或者稀疏的Q⁻¹ 也能提前算好整体开销进一步下降。不过要提醒的是Woodbury 那一步成立的默认条件是 Q 可逆。如果过程噪声在某些方向上为零也就是系统在某些方向上是确定演化的那么 Q 奇异这条路走不通。这时候常见的处理是对 Q 做正则化加上一个很小的对角项或者改用奇异值分解的形式来规避。我自己在刚体动力学建模里遇到过这种情况姿态的四元数部分没有过程噪声但位置部分有处理方式是把状态拆成两个子块分别推进。4.3 控制输入怎么接进来控制项 Bu 的接入方式很直接因为它只影响均值不影响协方差。在信息向量更新里可以先算出预测均值 μ Aμ Bu再乘上新的信息矩阵得到 η。如果你在实现上维护的是 (μ, Σ) 和 (η, Λ) 两套量这个步骤会更顺用矩形式推进均值和控制用信息形式的公式算出 Λ然后用 Λμ 更新 η。这里有一个经常被忽略的细节。控制输入的误差也就是执行器噪声应该并进 Q 里而不是并进 B 里。很多人会把执行器噪声写成 B 的扰动这在推导上等价于状态相关的噪声和标准的加性高斯白噪声假设不匹配。正确的做法是把控制噪声 u_noise 通过 B 投影到状态空间让 Q 增加 B·Σ_u·Bᵀ 这一项。这样处理后 Q 一般会变成半正定而非正定也就回到上一节讨论的奇异问题。5. 两种滤波器的工程对照与选型5.1 计算量、初始化与数值稳定性对照表我把常见维度的开销和特性整理成一张表供选型时参考。表中的 n 是状态维度m 是观测维度。维度标准卡尔曼滤波信息滤波状态参数(μ, Σ)(η, Λ)预测开销O(n³) 相似变换无求逆两次 O(n³) 求逆更新开销O(n³) 求逆卡尔曼增益O(mn²) 秩更新加法多传感器融合串行需中间态传递并行独立加项初始状态Σ 必须正定可逆Λ 可为近似零表示无信息数值优势场景观测噪声大、观测稀疏观测精度高、观测密集输出均值直接可得需要一次 Λ⁻¹η关于初始化这一点值得多讲几句。标准卡尔曼滤波里初始协方差必须正定否则第一次更新就会出问题。但在信息滤波里理论上 Λ 0 是完全合法的状态它表示我对这个状态没有任何先验知识此时信息向量 η 也为零。随着观测一个个进来Λ 从零开始逐步建起来。这个特性在分布式估计里是杀手锏所有节点可以约定初始信息为零各自贡献自己的观测增量谁先上线谁先加完全不需要协商一个共同的初始协方差。这个模式在传感器网络里几乎是标配。数值稳定性上信息滤波在观测精度极高的时候表现更好。原因是当 R 很小时HᵀR⁻¹H 的量级会非常大Λ 保持在一个很大的数值范围浮点数的表示相对稳定。而标准卡尔曼在同样情况下卡尔曼增益会趋近一个极限值协方差矩阵的元素会变得极小容易触碰浮点精度下限。我做过一个对照实验用双精度浮点跑一个测距精度到毫米级的定位问题卡尔曼形式在几步之后协方差出现了轻微的非对称而信息形式跑了几百步仍然是对称的。5.2 木村滤波为什么要维护两套参数有一类变种叫木村滤波Kimura Filter它同时维护 (μ, Σ) 和 (η, Λ) 两套参数用矩形式做预测、用信息形式做更新再在每步之后做一次一致性同步。这样既避免了预测中的求逆又保留了更新中的加法优势。同步的方式很简单从最新的一套参数算出另一套。如果当前有 (μ, Σ)就令 Λ Σ⁻¹、η Λμ如果当前有 (η, Λ)就令 μ Λ⁻¹η、Σ Λ⁻¹。逻辑上无懈可击代价是每一步都多了一次矩阵求逆实际上把信息滤波预测步骤省下来的开销又还回去了。那木村滤波还有意义吗有的但场景很窄。它的价值在于当预测步骤可以被解析简化时比如 A 是正交矩阵或者对角矩阵AΛ⁻¹Aᵀ 可以直接从 Λ 的对角元换算出结果不需要做完整求逆。这时候木村滤波既得到了预测的便宜也得到了更新的便宜。如果你的系统结构允许这种简化值得花时间做一做否则老老实实用一种形式就好两套参数同步带来的复杂度和潜在的数值误差往往得不偿失。6. 用 numpy 把整套推导跑一遍6.1 核心类实现下面是一个最小可运行的实现状态维度 n 和观测维度 m 都可以动态指定。我刻意没有用任何估计库全部手写方便对照上面的公式。import numpy as np class InformationFilter: def __init__(self, n, eps1e-8): self.n n # 用极小对角项代替严格零信息避免求逆时奇异 self.Lambda np.eye(n) * eps self.eta np.zeros(n) def to_moment(self): Sigma np.linalg.inv(self.Lambda) mu Sigma self.eta return mu, Sigma def predict(self, A, Q, BNone, uNone): mu, Sigma self.to_moment() mu_pred A mu if B is not None and u is not None: mu_pred mu_pred B u Sigma_pred A Sigma A.T Q self.Lambda np.linalg.inv(Sigma_pred) self.eta self.Lambda mu_pred def update(self, z, H, R): Rinv np.linalg.inv(R) self.Lambda self.Lambda H.T Rinv H self.eta self.eta H.T Rinv z def state(self): mu, _ self.to_moment() return mu这段代码里有两个细节值得单拎出来说。第一个是初始化时那个 eps它对应零信息的近似实现。严格零信息会导致 to_moment 里的求逆失败用一个极小值替代后初始协方差约等于 1/eps 倍的单位矩阵效果上就是非常不确定随着观测进来会被迅速压制下去。eps 选多大有讲究太大相当于引入了不该有的先验太小会放大浮点误差我一般取 1e-8 到 1e-6 之间具体看状态的物理量纲。第二个是 update 里完全没有出现卡尔曼增益这直接对应上一节的推导结论更新的全部内容就是两次加法。你可以把这段和标准卡尔曼实现放在一起对照会发现信息形式少了整整齐齐一大块代码。6.2 一个二维匀速运动模型的跟踪实验我构造了一个最简单的场景来验证一个二维平面上做匀速直线运动的点目标状态是 [x, y, vx, vy]。过程噪声用一个小的对角矩阵观测是每步都能测到位置噪声协方差也是对角阵。n 4 dt 0.1 A np.array([[1, 0, dt, 0], [0, 1, 0, dt], [0, 0, 1, 0], [0, 0, 0, 1]]) Q np.diag([1e-4, 1e-4, 1e-3, 1e-3]) H np.array([[1, 0, 0, 0], [0, 1, 0, 0]]) R np.diag([0.01, 0.01]) inf_filter InformationFilter(n) true_state np.array([0.0, 0.0, 1.0, 0.5]) np.random.seed(7) for k in range(200): true_state A true_state np.random.multivariate_normal(np.zeros(n), Q) z H true_state np.random.multivariate_normal(np.zeros(2), R) inf_filter.predict(A, Q) inf_filter.update(z, H, R) print(最终估计:, inf_filter.state())跑下来位置估计会稳定收敛到真值附近速度估计略慢一些但也在几步之内贴合。这个场景没什么难度重点是用它来确认代码逻辑正确因为最简单的情况最容易暴露符号错误。我建议每个第一次实现信息滤波的人都先跑这种最简场景别一上来就上真实的复杂模型否则出了问题根本分不清是公式推错了还是模型设计有问题。6.3 与标准卡尔曼滤波的一致性交叉验证真正有价值的验证是拿同样的数据同时喂给两套实现逐步对比状态估计。理论保证是两者结果完全一致任何偏差都说明代码有问题。class KalmanFilter: def __init__(self, x0, P0): self.x x0.copy() self.P P0.copy() def predict(self, A, Q): self.x A self.x self.P A self.P A.T Q def update(self, z, H, R): S H self.P H.T R K self.P H.T np.linalg.inv(S) self.x self.x K (z - H self.x) self.P (np.eye(len(self.x)) - K H) self.P然后用同一组模拟数据跑两条线逐步比较输出的均值和协方差。我第一次跑这个对比的时候发现三十步之后开始出现 1e-6 量级的偏差当时以为是公式推错了排查了大半天最后发现问题出在 eps 那个初始值上因为信息滤波的初始 Λ 是 eps 倍的单位阵等效初始协方差是 1/eps 倍的单位阵那个数值和卡尔曼形式里我拍的 P0 不完全相等所以两边起点就不一样。把 P0 设成和信息滤波等效的初始协方差之后两条轨迹贴合到小数点后十位以上。这个坑其实挺典型。信息滤波的初始状态是个不容易直观对应的量你很难像卡尔曼那样直接说初始位置的不确定度是 1 米因为信息矩阵的对角元是世界坐标系的精度而不是某个具体物理量的方差。工程上一般会反过来做先想清楚初始协方差 P0 是多少再取 Λ0 P0⁻¹ 作为起点这样思路更顺。7. 实操里最容易踩的几个坑7.1 信息矩阵奇异与零信息初始化第一个坑前面提过这里展开讲一下处理策略。严格零信息初始化在理论上合法但在实现上会导致求逆失败尤其是第一次预测的时候。三种常见的处理方式一是加极小正则项简单粗暴但会引入微小的先验偏差二是第一次预测跳过直接从第一个观测开始积累三是用一个独立的、极低置信度的先验比如把状态定义在一个很大的球形区域内取协方差为单位阵乘以一个大数。我自己的偏好是第二种和第三种结合。用一个不太大的先验协方差起步同时在第一次预测前不做求逆直接跳过把第一次的 Λ 定为初始值。这样可以避免那个极小正则项随迭代不断被放大。有一次我在一个长时间运行的系统中用了正则项跑了几个小时之后发现估计开始慢慢偏移追踪下来是因为那个 eps 在信息矩阵里始终占着一份虚假的确定性随着观测的贡献被反复累加这份虚假先验的影响在特定方向上被放大了最终表现成了缓慢漂移。提示如果你的系统需要长时间不间断运行尽量避免用正则项处理奇异改用显式的初始化流程把先验这件事说清楚。7.2 观测精度极高时的数值问题第二个坑是关于观测噪声 R 非常小的情况。举个数如果测距精度到毫米级那么 R 的对角元大概在 1e-6 量级R⁻¹ 的对角元在 1e6 量级。这时 HᵀR⁻¹H 的每个元素都会非常大和过程中累积的其他信息项相加时小的那部分会被浮点精度吃掉。这个现象在短期看不出来但长时间运行之后会导致两个症状一是数值上本该对称的信息矩阵出现轻微不对称因为加法的顺序不同引入了舍入误差二是本该正定的矩阵出现微小的负特征值下一次求逆就会报错或者得到荒谬的结果。对付这个问题的标准做法是做对称化每步更新之后显式地把 Λ 换成 (ΛΛ)/2把不对称的部分抹平。如果条件允许还可以把观测噪声协方差的对角元向上抬一点点比如从 1e-6 抬到 1e-5用一点点统计上的保守换取数值上的稳定性。我做过对比抬掉半个数量级对最终估计精度的影响在可接受范围内但引起的数值崩溃风险大幅下降。7.3 常见问题速查表我把实际项目中遇到的高频问题和对应处理整理如下方便快速对照排查。症状可能原因排查与处理首次预测报奇异矩阵错误零信息初始化加极小正则项或跳过首次预测估计出现固定偏差均值反解时符号错或 η 与 μ 混用检查 μ Λ⁻¹η 的实现长期运行后缓慢漂移正则项残留的虚假先验改用显式初始化流程信息矩阵非对称R 很小时浮点误差累积每步做 (ΛΛᵀ)/2 对称化后验置信区间过窄观测噪声相关未建模加入互协方差项单步估计跳变剧烈Q 或 R 量级不匹配重新标定过程噪声与观测噪声更新后 Λ 出现负特征值数值病态检查 R 是否过小必要时加下界这张表里最难排查的是最后一项。理论上 Λ 是若干半正定矩阵之和不可能是负定的但在数值误差下确实会出现微小的负特征值。发现这个症状时不要急着改算法先确认是不是 R 过小导致的病态如果是从噪声标定入手比从数值技巧入手更靠谱。另外补充一个我遇到过的特殊情况。有一次系统需要处理来自不同时间戳的观测旧观测要延迟才能处理这时候如果直接按到达顺序更新会导致信息矩阵的加法顺序和时间顺序不一致。在标准卡尔曼里这会引起混淆因为后一个观测要先解算前一个的状态。但在信息滤波里反而更简单只要每个观测的信息增量按它自己的时刻计算然后统一加到当前信息矩阵里就行不需要维护任何中间态。这个特性是异步传感器融合里非常有价值的如果你正在做多传感器的时间对齐信息形式会替你省掉很多麻烦。最后分享一个我在实际做传感器标定时用的技巧。当你需要在线估计一个静止的标定参数比如两个传感器之间的外参可以用信息滤波在参数空间上做增量更新每个新观测贡献一份信息增量等系统运行一段时间后信息矩阵的逆就是标定参数的协方差。这个做法最大的好处是随时可以看到当前的信息量当某个方向的信息量已经饱和时就可以停止采集数据了不用像批量最小二乘那样反复重算整个批次的解。结尾我从第一版能跑通的信息滤波实现到现在稳定的生产版本前后大概迭代了三四次每次都是在真实系统里暴露出问题之后才回来改。回头看最难的地方不是公式推导而是那些从公式里看不出来的东西比如零信息初始化的具体实现、极小正则项带来的长期漂移、高精度观测下的数值崩溃。这些经验没有一篇论文会写只能靠自己在一遍遍的调试里攒出来。如果你正准备在自己的项目里引入信息滤波我的建议是先在一维或者二维的玩具模型上把整个流程跑通然后拿一个真实的、有明确物理量的系统去验证最后再考虑分布式和异步的场景。顺序反过来大概率会在某个环节卡住找不到原因。
上一篇/下一篇内容由系统自动关联
返回资讯列表 →