3. 训练后量化(PTQ):PTQ原理、校准数据集、KL散度与熵校准、PTQ vs QAT对比
好,咱们进入第三个章节。训练后量化,英文叫 Post-Training Quantization,简称 PTQ。这名字起得很直白——训练完了,再来量化。说白了,就是模型已经训好了,我们拿着这个“成品”去做压缩。
我个人习惯把 PTQ 看作是“性价比之王”。为什么这么说?你想想看,不需要重新训练,不需要动你的训练代码,只需要跑几遍推理,就能把模型从 FP32 压到 INT8,推理速度翻倍甚至翻三倍。我在项目中遇到过不少团队,模型训了半个月,一听说要 QAT(量化感知训练)还得再训几天,直接摇头。这时候 PTQ 就是他们的救星。
3.1 PTQ 的核心原理
PTQ 的原理其实不复杂。我们有一组训练好的浮点权重,现在要把它映射到 INT8 的整数空间。这个映射过程,核心就是找两个东西:缩放因子(scale)和零点(zero point)。
公式很简单:
q = round(r / scale) + zero_point
其中 r 是浮点数,q 是量化后的整数。反过来,反量化就是:
r = (q - zero_point) * scale
嗯,这里要注意:scale 怎么选?选大了,精度损失大;选小了,容易溢出。所以 PTQ 的核心工作,就是找到最合适的 scale 和 zero_point。
那怎么找呢?这就需要用到校准数据集了。
3.2 校准数据集:PTQ 的“试金石”
校准数据集,英文叫 Calibration Dataset。它不是用来训练的,而是用来“试探”模型在真实数据上的激活值分布。
我刚开始做 PTQ 时犯过一个错误:随便拿了几张图就跑校准。结果量化后的模型在测试集上直接崩了。后来才明白,校准数据集必须满足两个条件:
- 代表性:数据分布要和真实部署场景一致。比如你做自动驾驶,校准集里全是晴天白天的图,那模型到了雨天晚上肯定拉胯。
- 多样性:覆盖尽可能多的输入模式。不要只用一类样本。
一般建议校准集的大小在 100~500 张左右。太少,统计不准;太多,校准时间太长,收益也不大。
3.3 KL 散度与熵校准
好,校准集有了,接下来怎么选 scale?最常用的方法之一就是KL 散度校准,也叫熵校准。
为什么用 KL 散度?说白了,就是衡量两个分布之间的“距离”。我们希望量化后的 INT8 分布,尽可能接近原始的 FP32 分布。KL 散度越小,说明量化损失越小。
具体做法是这样的:
- 在校准集上跑一遍推理,收集每一层的激活值分布。
- 把这个分布做成直方图,比如 2048 个 bin。
- 尝试不同的阈值 T,把直方图截断到 [-T, T] 范围内。
- 将截断后的分布量化到 256 个 bin(对应 INT8)。
- 计算量化前后的 KL 散度。
- 选择 KL 散度最小的那个 T,作为 scale 的依据。
你可能会问:为什么要截断?因为 FP32 的分布往往有长尾,那些极少出现的极端值如果保留,会浪费 INT8 的表示范围。截断掉尾部,反而能提高中间区域的精度。
TensorRT 默认使用的就是 KL 散度校准。我记得第一次用 TensorRT 做 PTQ 时,看到它自动选出来的阈值,跟我手动调了好几天才找到的几乎一样——那一刻,我承认我服了。
3.4 PTQ vs QAT 对比
讲完了 PTQ,咱们来聊聊它和 QAT(量化感知训练)的区别。很多同学问我:到底该用 PTQ 还是 QAT?
我的回答是:先试 PTQ,不行再上 QAT。
为什么?看这张对比表你就明白了:
| 对比维度 | PTQ(训练后量化) | QAT(量化感知训练) |
|---|---|---|
| 是否需要训练 | 不需要 | 需要,在量化模拟下微调 |
| 所需数据 | 少量校准集(100~500张) | 需要训练集或大量数据 |
| 实现复杂度 | 低,几行代码搞定 | 高,需要修改训练代码 |
| 精度损失 | 通常较小,大模型损失更小 | 更小,接近 FP32 精度 |
| 适用场景 | 快速部署、大模型、资源紧张 | 精度敏感、小模型、有训练资源 |
| 推理速度 | 快(INT8 加速) | 快(INT8 加速) |
你看,PTQ 最大的优势就是“快”和“省”。不需要动训练流程,不需要 GPU 跑几天微调。对于大模型(比如 ResNet-50 以上),PTQ 的精度损失往往在 1% 以内,完全可接受。
但 QAT 也有它的用武之地。我曾经在一个轻量级模型(MobileNetV2)上试过 PTQ,精度直接掉了 5 个点。为什么?小模型的表示能力弱,量化带来的噪声影响更大。这时候 QAT 就派上用场了——通过在训练中模拟量化误差,让模型学会“适应”量化。
最后总结一下我的经验:
- 模型大于 50MB:优先 PTQ,大概率够用。
- 模型小于 10MB:直接上 QAT,别犹豫。
- 中间地带:先 PTQ 试水,精度损失超过 2% 再切 QAT。
好了,PTQ 的原理、校准集、KL 散度、以及和 QAT 的对比,咱们都聊透了。下一章我会带你手把手跑一遍 PTQ 的代码,看看实际效果如何。