4、语音识别基础:MFCC特征提取原理、语音端点检测(VAD)、关键词唤醒(KWS)算法简介

各位同学,欢迎来到第四章。这一章我们聊聊语音识别的底层逻辑。

说实话,做智能家居语音控制,你不需要从零写一个语音识别引擎。但如果你不懂MFCC、VAD、KWS这三个东西,你连调试都无从下手。我在项目里见过太多人,模型跑不起来就怪硬件,其实是前端特征没处理好。

今天我们就把这三大块掰开揉碎。放心,不堆公式,咱们讲人话。

4.1 MFCC特征提取:让机器听懂你的声音

人耳听到声音,和麦克风采集到的波形,是两码事。麦克风录的是时域波形,但人耳真正敏感的是频域信息——说白了,就是不同频率的能量分布。

MFCC(梅尔频率倒谱系数)就是干这个的。它把一段语音,变成一组能代表「人耳听感」的特征向量。

4.1.1 提取流程(五步走)

  1. 预加重:提升高频部分。因为人在说话时,高频能量天然偏低,预加重就是给它补一补。我习惯用系数0.97,经验值。
  2. 分帧加窗:语音是非平稳信号,但短时间(20-30ms)内可以看作平稳。所以切成帧,每帧25ms,帧移10ms。加窗是为了减少频谱泄露,汉明窗最常用。
  3. FFT变换:把时域信号转到频域,得到频谱。
  4. 梅尔滤波器组:这是核心。梅尔刻度模拟了人耳对频率的非线性感知——低频分辨力高,高频分辨力低。把频谱通过一组三角滤波器,得到每个频带的能量。
  5. 取对数 + DCT:取对数是为了模拟人耳对响度的对数感知。DCT(离散余弦变换)则把能量去相关,得到最终的MFCC系数。通常取13维。

重要:MFCC不是原始语音,而是「特征」。就像你把一张照片压缩成一组数字,机器用这些数字去识别内容。

4.1.2 我在项目中踩过的坑

有一次,我在做远场语音唤醒,发现安静环境下识别率很高,但一开空调就崩。查了两天,最后发现是MFCC的帧长设得太短。空调噪声是低频连续的,帧长太短导致频谱分辨率不够,噪声和语音混在一起分不开。

后来我把帧长从20ms调到30ms,帧移从10ms调到15ms,问题解决了。嗯,有时候参数调一调,效果差很多。

小技巧:如果你用Python做原型,推荐python_speech_features库,一行代码就能提取MFCC。但量产时建议用C实现,比如CMSIS-DSP库里的MFCC函数,效率高很多。

4.2 语音端点检测(VAD):找到说话的起止点

VAD,说白了就是判断「现在是不是有人在说话」。智能家居设备不能一直录音,那样功耗扛不住,而且会把背景噪声也送进识别引擎。

4.2.1 传统VAD方法

  • 能量阈值法:计算每帧的短时能量,超过阈值就认为有语音。简单粗暴,但噪声大时容易误判。
  • 过零率:清音(如/s/、/f/)的过零率高,浊音(如/a/、/o/)的过零率低。结合能量用,效果更好。
  • 谱熵法:语音的频谱熵比噪声低,因为语音有结构。这个方法抗噪性不错,但计算量稍大。

4.2.2 现代VAD:基于DNN

现在主流方案是用轻量级神经网络做VAD。比如WebRTC的VAD模块,或者TensorFlow Lite Micro上跑的DNN-VAD。我个人的习惯是:

  • 如果MCU算力够(比如Cortex-M7以上),用DNN-VAD,准确率高。
  • 如果算力有限(比如Cortex-M0),用能量+过零率组合,调好阈值也能用。

注意:VAD的响应速度很关键。如果VAD判断「语音开始」慢了200ms,用户会觉得设备反应迟钝。我在一个项目里把VAD的帧长从30ms降到20ms,延迟从180ms降到了120ms,用户体验明显提升。

4.3 关键词唤醒(KWS):让设备「听到」你叫它

KWS就是「小爱同学」「Hey Siri」这类唤醒词的识别。它和完整语音识别的区别在于:KWS只识别几个固定的词,所以可以做得非常轻量,在MCU上实时运行。

4.3.1 经典KWS算法

算法特点适用场景
基于HMM(隐马尔可夫模型)传统方法,需要手工设计特征,调参麻烦算力极低的MCU
基于DNN/CNN端到端,准确率高,但需要一定算力Cortex-M4以上
基于TCN(时序卷积网络)比CNN更擅长处理时序,模型小资源受限但要求高精度
基于Transformer(轻量版)最新趋势,但MCU上还不太成熟未来方向

4.3.2 我推荐的做法

如果你现在要做一个智能家居的KWS,我建议直接用TensorFlow Lite Micro + 预训练模型。Google提供了几个现成的唤醒词模型,比如「Hey Google」的模型,你只需要微调一下换成自己的唤醒词就行。

我曾经在一个项目里自己从零训练KWS模型,折腾了两个月,效果还不如人家预训练模型微调一周的好。所以,别重复造轮子。

关键指标:KWS有两个核心指标——唤醒率(该醒的时候醒了)和误唤醒率(不该醒的时候醒了)。这两个是矛盾的,你需要根据产品场景做权衡。比如智能音箱,误唤醒很烦人,所以宁可降低唤醒率也要压低误唤醒。但智能灯,用户喊几次没反应更烦,所以唤醒率优先。

4.4 三者的协作流程

在实际系统中,这三个模块是串联工作的:

  1. 麦克风采集音频 → 送入VAD模块
  2. VAD检测到语音开始 → 开始缓存音频数据
  3. 缓存的数据送入MFCC提取模块 → 得到特征序列
  4. 特征序列送入KWS模块 → 判断是否包含唤醒词
  5. 如果匹配唤醒词 → 启动完整的语音识别流程

你看,VAD负责「什么时候开始听」,MFCC负责「把声音变成机器能理解的特征」,KWS负责「判断是不是在叫我」。三个环节缺一不可。

实战建议:在调试阶段,先把VAD和MFCC的输出可视化出来。我习惯用Python的matplotlib画一下能量曲线和MFCC热力图,一眼就能看出特征提取有没有问题。等VAD和MFCC调好了,再上KWS模型,否则你根本不知道是哪个环节出了问题。

好了,这一章就到这里。下一章我们讲语音信号预处理实战——怎么在MCU上高效实现这些算法。到时候我会给出一份完整的C代码示例,咱们手把手调通。


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