1. 音频基础概念:声音的物理特性、采样率与位深度、PCM编码原理、音频文件格式概览
做嵌入式音频开发,说白了就是跟声音打交道。但声音这东西看不见摸不着,你得先理解它的物理本质,才能知道怎么用代码去采集、处理和播放它。这一章我们就把基础打牢。
1.1 声音的物理特性
声音的本质是机械振动在介质中的传播。在空气中,它表现为疏密相间的纵波。我刚开始做音频驱动时,总觉得这些物理概念离代码很远,直到有一次调试麦克风阵列,发现采集到的波形全是噪声——后来才意识到是腔体共振频率没处理好。嗯,物理这东西,绕不过去。
声音有三个核心物理参数:
- 频率(Frequency):单位Hz,决定音调高低。人耳可听范围约20Hz~20kHz。低于20Hz叫次声波,高于20kHz叫超声波。
- 振幅(Amplitude):决定响度大小。单位dB(分贝),0dB是人耳能听到的最小声压。
- 相位(Phase):描述波形在时间轴上的偏移。单位度或弧度。相位差在立体声和降噪算法中非常关键。
关键记忆点:频率决定音调,振幅决定响度,相位决定空间感。这三个参数是后续所有音频处理的基础。
1.2 采样率与位深度
模拟声音是连续的,但计算机只能处理离散的数字信号。怎么把连续信号变成离散数据?靠采样和量化。
采样率(Sample Rate)
采样率就是每秒采集多少个样本点。单位Hz。根据奈奎斯特采样定理:采样率必须大于信号最高频率的2倍,才能无失真地重建原始信号。
| 采样率 | 常见用途 | 最高可还原频率 |
|---|---|---|
| 8 kHz | 电话语音 | 4 kHz |
| 16 kHz | VoIP、语音识别 | 8 kHz |
| 44.1 kHz | CD音质音乐 | 22.05 kHz |
| 48 kHz | DVD、专业音频 | 24 kHz |
| 96 kHz | 高解析音频 | 48 kHz |
我的经验:在嵌入式Linux项目中,语音采集我习惯用16kHz,因为人声主要能量集中在4kHz以下,16kHz采样绰绰有余,还能节省CPU和内存。音乐播放则用44.1kHz或48kHz。
位深度(Bit Depth)
位深度决定每个采样点的精度。说白了,就是用一个多少位的整数来表示振幅大小。
- 8位:256个量化等级,动态范围约48dB。噪声明显,基本不用。
- 16位:65536个量化等级,动态范围约96dB。CD标准,嵌入式常用。
- 24位:16777216个量化等级,动态范围约144dB。专业录音用。
- 32位:浮点或定点,动态范围极大。多用于音频处理内部。
避坑指南:我曾经在一个项目里用了8位采样,结果回放时底噪大到无法接受。后来换成16位,问题立刻解决。记住:嵌入式音频最低用16位,别省那点存储空间。
1.3 PCM编码原理
PCM(Pulse Code Modulation,脉冲编码调制)是最原始、最直接的音频数字编码方式。它不做任何压缩,就是把模拟信号采样、量化、编码成二进制数据。
PCM的编码流程分三步:
- 采样:按固定时间间隔采集模拟信号的瞬时值。
- 量化:将采样值映射到离散的量化等级上。
- 编码:将量化值转换成二进制码字。
举个例子:一个16位、44.1kHz、单声道的PCM音频流,每秒产生的数据量是:
44.1 kHz × 16 bit × 1 channel = 705.6 kbps
换算成字节:705.6 / 8 = 88.2 KB/s
你想想看,一首3分钟的歌曲,光PCM数据就要15.8MB。这就是为什么需要压缩格式。
PCM数据在内存中的排列方式:
- 小端序(Little-Endian):低字节在前,高字节在后。x86/ARM默认。
- 大端序(Big-Endian):高字节在前,低字节在后。网络字节序。
- 交错模式(Interleaved):左右声道数据交替排列。L R L R L R ...
- 非交错模式(Non-Interleaved):先存完左声道所有样本,再存右声道。L L L ... R R R ...
我个人习惯在嵌入式Linux中使用小端序、交错模式的16位PCM。ALSA驱动默认就是这个格式,省去转换的麻烦。
1.4 音频文件格式概览
音频文件格式本质上就是PCM数据的容器,加上一些元数据头。我整理了一张对比表,方便你快速了解:
| 格式 | 扩展名 | 压缩方式 | 典型用途 | 嵌入式适用性 |
|---|---|---|---|---|
| WAV | .wav | 无压缩(PCM) | Windows、专业音频 | ★★★★★ 最常用 |
| MP3 | .mp3 | 有损压缩 | 音乐播放 | ★★★★ 需解码库 |
| AAC | .aac/.m4a | 有损压缩 | 视频、流媒体 | ★★★ 需解码库 |
| FLAC | .flac | 无损压缩 | 高保真音乐 | ★★★ 需解码库 |
| OGG | .ogg | 有损/无损 | 开源项目 | ★★ 需解码库 |
| RAW | .raw/.pcm | 无头PCM | 裸数据交换 | ★★★★★ 最灵活 |
我的建议:在嵌入式Linux开发调试阶段,优先用WAV格式。它结构简单,没有编解码开销,用hexdump就能直接看数据。等调通了再考虑加MP3或AAC解码库。
WAV文件头结构(44字节)是每个嵌入式音频工程师必须手写的:
Offset Size Description
0 4 "RIFF" 标识
4 4 文件总大小 - 8
8 4 "WAVE" 标识
12 4 "fmt " 子块标识
16 4 子块1大小(16 for PCM)
20 2 音频格式(1 = PCM)
22 2 声道数
24 4 采样率
28 4 字节率
32 2 块对齐
34 2 位深度
36 4 "data" 子块标识
40 4 PCM数据大小
我曾经在调试一个USB音频设备时,发现播放出来的声音全是噪声。用hexdump一看,WAV头里的字节率算错了——声道数写成了2但数据是单声道。这种低级错误,排查起来最费时间。
知识体系总览
下面这张图把本章的核心概念串起来了,你可以把它当作后续学习的导航图:
这一章的内容是后续所有音频开发的基础。采样率和位深度决定了音频质量的上限,PCM编码是理解所有音频数据流的起点,文件格式则是你与存储和网络打交道的接口。把这些概念吃透,后面写驱动、调ALSA、做音频处理时,你心里就有底了。