2. 编码框架与核心模块:混合编码框架总览、帧内预测、帧间预测、变换量化、环路滤波、熵编码
各位好,欢迎来到第二章。这一章我们直接切入 H.265 的心脏——混合编码框架。说白了,就是视频编码器到底是怎么把一张张图片压成比特流的。我当年刚接触 HEVC 时,看着那一堆模块也头大。但拆开来看,其实就六个核心模块在轮流转。
核心观点:HEVC 沿用了经典的“预测 + 变换 + 熵编码”混合框架。这不是新发明,而是把 H.264 的架构做了深度优化。每个模块都有改进,但整体逻辑没变。
2.1 混合编码框架总览
先看整体流程。输入一帧图像,编码器会做这几件事:
- 分块:把图像切成 CTU(编码树单元),大小从 64×64 到 8×8 不等。
- 预测:用帧内或帧间方式,猜出当前块的样子。
- 残差计算:原始块减去预测块,得到残差。
- 变换量化:对残差做 DCT 变换,再量化,丢掉人眼不敏感的高频信息。
- 熵编码:把量化后的系数、模式信息等压缩成二进制流。
- 环路滤波:重建图像时做去块效应和 SAO 滤波,提升参考帧质量。
下面这张图把整个流程串起来了。我建议你把它当作编码器的“地图”,后面每个模块都能在这张图上找到位置。
我的经验:刚开始学框架时,别死记硬背每个模块的细节。先记住“预测→残差→变换→量化→熵编码”这条主线。后面每个模块都会展开讲,到时候再回来对照这张图,理解会深很多。
2.2 帧内预测
帧内预测,说白了就是用当前帧里已经编好的像素,来猜当前块的样子。HEVC 支持 35 种预测模式,比 H.264 的 9 种多了不少。
| 预测模式 | 数量 | 说明 |
|---|---|---|
| Planar | 1 | 平滑渐变,适合平坦区域 |
| DC | 1 | 取平均值,适合大面积均匀区域 |
| 角度模式 | 33 | 覆盖从近水平到近垂直的各个方向 |
为什么需要这么多角度?你想想看,视频里的纹理方向千变万化。如果只有几个固定角度,很多纹理就预测不准,残差变大,码率自然就上去了。HEVC 把角度细分到每 5.6 度一个,基本能覆盖大多数自然纹理的方向。
关键点:帧内预测的精度取决于参考像素的质量。参考像素离当前块越近,相关性越强,预测越准。所以编码顺序是从左上到右下,逐块推进。
2.3 帧间预测
帧间预测是视频压缩的“主力军”。它利用时间上的冗余——相邻帧之间内容变化不大,只需要传“变化的部分”就行。
HEVC 的帧间预测有几个重要改进:
- 运动估计精度:支持 1/4 像素精度,插值滤波器更复杂,预测更准。
- Merge 模式:相邻块的运动信息可以共享,省掉不少比特。
- AMVP(高级运动向量预测):从候选列表中选最优的运动向量预测值。
我记得有一次做移动端编码器优化,发现帧间预测占了编码时间的大头。后来通过限制搜索范围和提前终止,才把速度提上来。这个后面性能调优章节会细讲。
注意:帧间预测虽然压缩效率高,但计算量也大。运动估计的搜索范围、精度、候选数,都会直接影响编码速度。实际项目中需要根据应用场景做权衡。
2.4 变换量化
预测做完后,残差信号还带着不少空间冗余。变换的作用就是把残差从像素域转到频域,让能量集中到低频系数上。
HEVC 使用整数 DCT(离散余弦变换),块大小支持 4×4、8×8、16×16、32×32。大块适合平坦区域,小块适合纹理复杂区域。
量化是真正“丢信息”的环节。量化参数 QP 越大,丢得越多,码率越低,但画质也越差。QP 范围是 0~51,每增加 6,码率大约减半。
// 量化过程的简化示意
// Qstep 由 QP 决定,QP 越大 Qstep 越大
coeff_quantized = round(coeff_dct / Qstep)
避坑指南:我曾经在低码率场景下把 QP 设得过高,结果画面出现严重的块效应。后来发现,配合合适的量化矩阵(加权量化),可以在保持主观质量的同时降低码率。这个技巧在 HEVC 里是支持的,但很多编码器默认没开。
2.5 环路滤波
环路滤波是编码器里的“美容师”。它不直接压缩数据,而是提升重建图像的质量,让后续的预测更准。
HEVC 包含两个滤波器:
- 去块效应滤波器(DBF):消除块边界上的不连续,让图像更平滑。
- 样本自适应偏移(SAO):补偿量化带来的像素偏移,恢复细节。
这两个滤波器都在编码环路内部,也就是说,它们处理后的图像会被用作后续帧的参考。所以滤波质量直接影响编码效率。
| 滤波器 | 作用 | 复杂度 |
|---|---|---|
| DBF | 平滑块边界 | 低 |
| SAO | 补偿像素偏移 | 中 |
我的习惯:在调试编码器时,我经常把环路滤波关掉,看看原始残差是什么样的。这样能快速定位问题出在预测阶段还是量化阶段。调优时再打开滤波,看最终效果。
2.6 熵编码
熵编码是编码器的最后一步。它把量化后的系数、模式信息、运动向量等,用尽量少的比特表示出来。
HEVC 只使用一种熵编码方式:CABAC(上下文自适应二进制算术编码)。H.264 还保留了 CAVLC 作为低复杂度选项,但 HEVC 认为 CABAC 的压缩效率优势足够大,不再保留备选。
CABAC 的核心思想是:根据已编码的符号,动态调整概率模型。高频出现的符号用短码,低频出现的用长码。这样整体码率就降下来了。
// CABAC 编码流程(极度简化)
1. 将语法元素二值化(变成二进制串)
2. 对每个 bin 选择上下文模型
3. 根据上下文概率进行算术编码
4. 更新概率模型
注意:CABAC 虽然压缩效率高,但它是串行处理的,很难并行化。硬件实现时,这个模块往往是瓶颈。软件实现的话,可以用多线程把不同 CTU 的熵编码分开做,但上下文模型不能跨 CTU 共享。
好了,这一章我们把 HEVC 的六个核心模块都过了一遍。每个模块都有它的设计哲学和工程权衡。后面几章会逐个深入,到时候你会发现,很多优化技巧都建立在对这些模块的深刻理解上。