第4章:零速检测算法

零速检测,说白了就是判断行人脚是不是「粘」在地上了。我刚开始做惯导时,觉得这步很简单——脚不动就是零速呗。后来发现,事情远没那么简单。

你想想看,人在走路时,脚掌落地那一瞬间,速度真的为零吗?其实不是。严格来说,脚底和地面接触时,会有微小的滑动和形变。我们说的「零速」,是一个近似状态。检测这个状态,就是零速检测算法的核心任务。

我个人习惯把零速检测算法分成五类。咱们一个一个来看。

4.1 加速度幅值检测法

这个方法最直观。当脚静止时,加速度计只感受重力。理想情况下,加速度幅值就是1g(约9.8 m/s²)。

判断逻辑很简单:

|acc_norm - g| < threshold_acc

其中 acc_norm 是加速度三轴幅值,g 是当地重力加速度,threshold_acc 是阈值。

我在项目中遇到过一个问题:阈值设得太小,正常走路时频繁漏检;设得太大,又把摆动阶段误判为零速。嗯,这里要注意,加速度幅值法对剧烈运动很敏感,但慢走时效果一般。

小技巧: 阈值通常取 0.5~1.5 m/s²。你可以先采集一段静止数据,看看加速度噪声有多大,再定阈值。

4.2 角速度幅值检测法

这个方法我更喜欢。为什么?因为脚落地时,角速度变化比加速度更明显。你想想看,脚在空中摆动时,角速度很大;一落地,角速度瞬间掉到接近零。

判断逻辑:

|gyro_norm| < threshold_gyro

角速度幅值法有个好处——对重力变化不敏感。你在斜坡上走,加速度幅值会变,但角速度幅值不会。我曾经在楼梯测试中吃过亏,加速度法频繁误判,换成角速度法就稳了。

注意: 角速度阈值一般取 0.5~1.5 rad/s。如果传感器噪声大,可以适当放宽。

4.3 加速度方差检测法

这个方法看的是加速度的「波动程度」。脚静止时,加速度值很稳定,方差小;脚运动时,加速度剧烈变化,方差大。

计算方式:

var_acc = variance(acc_x, acc_y, acc_z)  // 滑动窗口内计算方差
if var_acc < threshold_var:
    判定为零速

滑动窗口长度很关键。我建议取 5~10 个采样点(对应 0.05~0.1 秒)。窗口太短,方差不稳定;窗口太长,会延迟检测。

说实话,方差法单独用效果一般。我习惯把它和幅值法组合起来用。

4.4 组合检测法

这才是工程上最常用的方案。把加速度幅值、角速度幅值、加速度方差三个条件组合起来,同时满足才判定为零速。

逻辑如下:

if (|acc_norm - g| < th_acc) AND 
   (|gyro_norm| < th_gyro) AND 
   (var_acc < th_var):
    判定为零速
else:
    判定为运动

为什么用组合?因为单一方法都有盲区。加速度幅值法在斜坡上会误判,角速度法在慢速转身时可能漏检,方差法对高频噪声敏感。三个条件一组合,鲁棒性就上来了。

我在做室内定位项目时,用的就是组合检测法。实测下来,零速检测准确率从单方法的85%提升到了97%以上。

核心要点: 组合检测不是简单的「与」逻辑。你可以根据运动场景调整权重。比如跑步时,角速度阈值可以放大;慢走时,加速度方差阈值可以收紧。

4.5 自适应阈值设计

固定阈值有个硬伤——不同人走路习惯不同,不同地面材质也不同。你想想看,在水泥地上走和草地上走,传感器噪声能一样吗?

自适应阈值就是让算法自己「学习」阈值。我常用的方法有两种:

  1. 基于统计的自适应: 实时计算加速度和角速度的均值和标准差,阈值 = 均值 + k * 标准差。k 一般取 2~3。
  2. 基于运动强度的自适应: 用滑动窗口内的能量值来动态调整阈值。运动强度大时,阈值放宽;运动强度小时,阈值收紧。

代码实现思路:

// 滑动窗口内计算统计量
mean_acc = mean(window_acc)
std_acc = std(window_acc)
th_acc = mean_acc + 2.5 * std_acc

// 同样方法计算角速度阈值
mean_gyro = mean(window_gyro)
std_gyro = std(window_gyro)
th_gyro = mean_gyro + 2.5 * std_gyro

我曾经在自适应阈值上栽过跟头。有一次测试,用户突然从走路变成跑步,自适应阈值没跟上,导致连续漏检了好几步。后来我加了「阈值变化速率限制」,问题就解决了。

避坑指南: 自适应阈值不要更新太快。我建议每 0.5~1 秒更新一次,太频繁反而会引入噪声。

知识体系总览

下面这张图,是我梳理的零速检测算法知识结构。你可以看到,五种方法各有侧重,组合检测是工程落地的首选。

零速检测算法知识体系 零速检测算法 加速度幅值法 |acc_norm - g| < th 角速度幅值法 |gyro_norm| < th 加速度方差法 var_acc < th 组合检测法 AND 逻辑组合 自适应阈值 动态调整阈值 工程建议 组合检测法 + 自适应阈值 = 最佳实践 单一方法准确率约85%,组合后可达97%以上

好了,零速检测算法就讲到这里。每种方法都有它的脾气,你得根据实际场景去调参。下一章,咱们聊聊零速修正的具体实现——怎么用卡尔曼滤波把零速信息用起来。


公众号:蓝海资料掘金营,微信deep3321