01 模型剪枝是什么?为什么深度模型需要剪枝?
一、为什么要研究模型剪枝?
近几年,深度学习模型的规模越来越大。
在计算机视觉中,从早期的 LeNet、AlexNet,到后来的 VGG、ResNet、DenseNet,再到 Vision Transformer,模型参数量和计算量不断增加。
在自然语言处理和大语言模型领域,这种趋势更加明显。从 BERT、GPT,到现在的百亿、千亿参数大模型,模型规模已经成为影响模型能力的重要因素之一。
模型变大,通常可以带来更强的表达能力和更好的任务性能。但是,模型变大也会带来一系列现实问题:
参数量大,占用存储空间高;
计算量大,推理速度慢;
显存占用高,部署成本高;
能耗高,不适合边缘设备;
训练和微调成本高;
在实际业务系统中响应延迟难以满足要求。
例如,一个模型在实验室 GPU 上可以顺利运行,并不意味着它能轻松部署到手机、摄像头、嵌入式设备、边缘服务器或者实时业务系统中。因此,深度模型压缩成为了一个非常重要的研究方向。常见的模型压缩技术包括:
| 压缩技术 | 核心思想 | 主要目标 |
|---|---|---|
| 模型剪枝 | 删除冗余参数或结构 | 减少参数量和计算量 |
| 模型量化 | 用低比特数表示权重和激活 | 降低存储和计算成本 |
| 知识蒸馏 | 用大模型指导小模型训练 | 提升小模型性能 |
| 低秩分解 | 用低秩矩阵近似原始权重 | 减少矩阵计算量 |
| 神经架构搜索 | 自动搜索轻量模型结构 | 获得高效网络架构 |
其中,模型剪枝是最经典、最直观、也最容易理解的一类模型压缩方法。一句话概括:
模型剪枝就是从一个已经训练好的大模型中,删除不重要或冗余的参数、通道、层、注意力头、Token 等结构,使模型变得更小、更快,同时尽量保持原有精度。
二、什么是模型剪枝?
“剪枝”这个词来自树木修剪。
一棵树如果枝叶过于繁茂,可能会消耗过多养分。通过剪掉不必要的枝条,可以让树的结构更加清晰,也能让主要枝干获得更多资源。神经网络中的剪枝思想类似。一个深度神经网络通常包含大量参数,但并不是每一个参数都同等重要。很多参数可能对最终预测结果影响很小,甚至存在明显冗余。模型剪枝的目标就是:找出模型中不重要的部分,然后将其删除,从而得到一个更轻量的模型。
以一个简单的全连接层为例:
其中,W 是权重矩阵,x 是输入特征,b 是偏置项。如果权重矩阵 W中有些元素非常接近 0,那么这些权重对输出的影响可能很小。我们可以将它们直接置为 0:
其中,是剪枝阈值。这就是最简单的基于权重幅值的剪枝思想:如果一个权重的绝对值很小,就认为它不重要,可以被剪掉。当然,实际模型剪枝远不止这么简单。现代剪枝方法不仅可以剪单个权重,还可以剪通道、卷积核、网络层、注意力头、Transformer 中的 Token,甚至可以剪掉大语言模型中的部分 MLP 神经元或 Transformer Block。
三、模型中到底有哪些冗余?
模型剪枝能够成立,一个核心前提是:深度神经网络中普遍存在大量冗余。
这种冗余可以体现在多个层面。
1. 参数冗余
很多神经网络的参数数量远远大于任务所需的最小参数数量。例如,VGG 网络拥有大量卷积层和全连接层,参数量非常大。虽然这种大模型能够取得不错效果,但其中很多参数可能并不是完成分类任务所必需的。因此,我们可以尝试删除一部分参数,让模型更加紧凑。
2. 通道冗余
在 CNN 中,一个卷积层通常会产生多个输出通道。每个通道可以看作一种特征检测器。但是,并不是所有通道都同样重要。有些通道可能学习到了边缘、纹理、形状等关键特征;有些通道可能只产生很弱的响应,或者和其他通道高度相似。对于卷积层:
其中,W是卷积核,X 是输入特征图,Y 是输出特征图。如果某个输出通道对最终分类结果影响很小,那么就可以删除这个通道,同时删除下一层中与该通道相连的卷积核部分。这类方法通常被称为通道剪枝。通道剪枝属于结构化剪枝,它不仅能减少参数量,也更容易带来实际推理加速。
3. 层冗余
随着网络越来越深,部分网络层可能并不是必须的。例如,在 ResNet、Transformer 等深层网络中,有些层对最终输出的贡献可能较小。如果直接删除这些层,模型性能可能只会轻微下降。这种剪枝方式叫做层剪枝或深度剪枝。在 Transformer 和大语言模型中,层剪枝尤其重要,因为每一层 Transformer Block 都包含多头注意力模块和前馈神经网络模块,计算成本较高。
4. 注意力头冗余
在 Transformer 中,多头注意力机制是核心结构。一个多头注意力层可以表示为:
每个注意力头为:
理论上,不同注意力头可以学习不同的关系模式。但实际上,很多研究发现,并不是所有注意力头都同等重要。有些注意力头可能高度冗余,删除之后对模型性能影响很小。因此,在 BERT、ViT、LLM 等模型中,注意力头剪枝是一个非常重要的方向。
5. Token 冗余
在 Vision Transformer 中,输入图像会被划分成多个 Patch,每个 Patch 对应一个 Token。假设输入图像被划分为 (N) 个 Token,那么自注意力计算复杂度大约为:
这意味着 Token 数量越多,注意力计算成本增长越快。但是,对于一张图像分类任务来说,并不是所有图像区域都同样重要。例如,一张猫的图片中,猫所在区域通常比背景墙面、天空、地板更加重要。ViT 中的一些 Token 可能对应背景区域,这些 Token 对最终分类结果贡献较小。因此,可以在推理过程中删除不重要的 Token,这就是Token 剪枝。Token 剪枝是 ViT 模型压缩中的一个重要方向。
四、模型剪枝的基本流程
一个典型的模型剪枝流程通常包括四个步骤:
原始模型训练 → 重要性评估 → 删除冗余结构 → 微调恢复精度
下面分别解释。
1. 训练原始模型
首先需要得到一个性能较好的原始模型,通常称为Baseline Model。例如:
ResNet-50 on ImageNet
BERT-base on GLUE
ViT-base on ImageNet
LLaMA on language modeling tasks
剪枝通常不是从零开始,而是在一个已经训练好的模型基础上进行。原因很简单:如果原始模型本身性能很差,那么剪枝之后的模型通常也不会好。
2. 计算重要性评分
剪枝的关键问题是:哪些参数或结构可以删除?
这就需要为模型中的不同单元计算重要性评分。常见的重要性评分方法包括:
| 方法 | 基本思想 |
|---|---|
| 权重幅值 | 权重绝对值越小越不重要 |
| 梯度信息 | 对损失影响越小越不重要 |
| Taylor 展开 | 估计删除某个结构后损失变化 |
| Hessian 信息 | 使用二阶信息衡量敏感度 |
| BN 缩放因子 | BN 的 gamma 越小,通道越不重要 |
| 激活统计 | 激活值越弱,贡献可能越小 |
| 重构误差 | 删除后特征变化越小越不重要 |
| 冗余度量 | 与其他结构越相似,越可能冗余 |
最简单的方法是基于权重幅值:
其中,表示权重
的重要性评分。如果
很小,就认为该权重不重要。更复杂的方法会考虑损失函数变化。例如,假设删除参数
后损失函数变化为:
如果很小,说明删除该参数对模型影响不大,因此可以剪掉。
3. 删除冗余结构
根据重要性评分,可以选择删除一部分参数或结构。
例如:
删除绝对值较小的权重;
删除响应较弱的通道;
删除贡献较小的注意力头;
删除冗余的 Transformer 层;
删除不重要的 ViT Token;
删除 LLM 中部分 MLP 神经元。
这个过程可以表示为:
其中:
M 表示原始模型;
S 表示重要性评分;
r 表示剪枝率;
M' 表示剪枝后的模型。
剪枝率 r 表示删除多少比例的参数或结构。例如: r = 50%。表示删除一半的参数或结构。
4. 微调恢复精度
剪枝会破坏原始模型结构,因此模型精度通常会下降。为了恢复性能,通常需要对剪枝后的模型进行微调:
其中,M''是微调后的最终模型。微调的作用类似于让模型重新适应被剪枝后的结构。不过,近年来也有很多方法研究免重训练剪枝或训练后剪枝,也就是剪枝之后不再进行完整微调,甚至不训练就直接使用。这在大模型和 ViT 部署中非常重要,因为大模型重新训练或微调的成本非常高。
五、模型剪枝可以分成哪些类型?
模型剪枝有很多分类方式。最常见的是按照剪枝粒度划分。
1. 非结构化剪枝
非结构化剪枝主要删除单个权重。
例如,一个权重矩阵为:
如果将绝对值小于 0.05 的权重置为 0,则得到:
这种剪枝方式可以得到稀疏矩阵。
优点是:
剪枝粒度细;
压缩率高;
对精度影响相对较小。
缺点是:
得到的是不规则稀疏结构;
普通 GPU/CPU 上不一定能直接加速;
需要专门的稀疏计算库或硬件支持。
所以,非结构化剪枝往往可以显著减少参数量,但不一定能显著降低实际推理延迟。
2. 结构化剪枝
结构化剪枝删除完整的结构单元,例如:
一个卷积通道;
一个卷积核;
一个残差块;
一个 Transformer 层;
一个注意力头;
一个 MLP 中间维度;
一组 Token。
例如,在 CNN 中删除一个输出通道:
原始卷积层输出通道数:64
剪枝后输出通道数:48
这意味着后续层的输入通道数也会随之减少,模型结构真正变窄。结构化剪枝的优点是:
模型结构规则;
更容易在普通硬件上加速;
更适合部署;
不需要特殊稀疏计算库。
缺点是:
剪枝粒度较粗;
对模型精度影响可能更大;
需要处理层与层之间的结构依赖。
在实际部署中,结构化剪枝通常比非结构化剪枝更受关注。
3. 半结构化剪枝
半结构化剪枝介于非结构化剪枝和结构化剪枝之间。典型例子是 NVIDIA GPU 支持的 2:4 稀疏模式。所谓 2:4 稀疏,是指每连续 4 个权重中保留 2 个,剪掉 2 个。例如:
[0.8, 0.1, -0.5, 0.03] → [0.8, 0, -0.5, 0]
这种方式比完全非结构化剪枝更加规则,也比完整通道剪枝更加灵活。
半结构化剪枝的目标是:在压缩率、精度保持和硬件加速之间取得平衡
六、为什么深度模型可以被剪枝?
很多人刚接触剪枝时会有一个疑问:如果一个模型中的参数都很重要,那剪掉之后不就一定会变差吗?这个问题很关键。实际上,深度模型之所以可以剪枝,主要有以下几个原因。
1. 深度模型通常过参数化
现代深度神经网络往往是过参数化的。所谓过参数化,是指模型参数数量远远超过训练数据所能严格约束的自由度。简单来说:模型拥有的参数太多了,多到其中一部分参数并不是必须的。
例如,一个分类任务可能并不需要上亿个参数也能完成。但是,为了让模型更容易训练、更容易优化、更容易获得高精度,我们通常会使用更大的网络。
这种大网络在训练完成后,内部往往存在大量冗余结构。
2. 不同神经元或通道之间存在功能重叠
在深度网络中,不同通道可能学到相似的特征。例如,在图像分类模型中,多个卷积通道可能都在检测类似的边缘、纹理或局部模式。如果两个通道的功能高度相似,那么删除其中一个通道,模型仍然可以依靠另一个通道完成类似的特征表达。这就是结构冗余。从这个角度看,剪枝不只是删除“不重要”的结构,也可以删除“和其他结构重复”的结构。这也是很多冗余感知剪枝方法的基本出发点。
3. 损失函数对某些参数不敏感
模型训练完成后,并不是所有参数的微小变化都会显著影响损失函数。如果某个参数发生变化时,损失函数几乎不变,那么这个参数就可以认为是不敏感的。用数学形式表示,如果删除某个参数
后:
那么说明该参数对当前任务影响较小,可以考虑剪掉。剪枝中的敏感度分析,本质上就是在估计:删除某个参数或结构后,模型损失会增加多少?如果增加很少,就说明可以剪。
4. 微调可以恢复部分性能
即使剪枝会导致精度下降,后续微调也可以帮助模型恢复性能。剪枝后,模型结构发生变化,但剩余参数仍然保留了大量有用知识。通过少量训练,模型可以重新调整剩余参数,使其适应新的紧凑结构。
七、模型剪枝到底想优化什么?
模型剪枝并不是简单地让模型变小,而是在多个目标之间做平衡。常见目标包括:
同时满足:
[
更直观地说,模型剪枝希望实现:
更小的模型
更低的计算量
更快的推理速度
更低的存储成本
更低的显存占用
尽可能不下降的精度
但这些目标并不总是一致。
例如:
参数量减少,不一定代表推理速度变快;
FLOPs 降低,不一定代表真实延迟降低;
剪枝率越高,模型越小,但精度可能下降越多;
非结构化剪枝参数少,但硬件不一定能高效利用;
结构化剪枝容易加速,但可能更容易损失精度。
所以,模型剪枝真正困难的地方在于:如何在精度、压缩率和实际加速之间取得平衡。
八、参数量、FLOPs 和推理速度不是一回事
很多初学者容易把参数量、FLOPs 和推理速度混为一谈。实际上,它们是三个不同概念。
1. 参数量
参数量表示模型中可学习参数的数量。
例如:ResNet-50 大约有 2500 万参数
BERT-base 大约有 1.1 亿参数
参数量主要影响:
模型文件大小;
显存占用;
存储成本;
部分计算成本。
但参数量少,不一定推理快。
2. FLOPs
FLOPs 表示浮点运算次数,常用于衡量模型理论计算量。
例如,一个卷积层的 FLOPs 大致与以下因素有关:
FLOPs 可以反映理论计算复杂度,但不等于真实推理速度。
3. Latency
Latency 表示模型实际推理一次所需要的时间。
它受到很多因素影响:
硬件类型;
算子是否高效;
内存访问开销;
并行度;
batch size;
框架优化;
是否支持稀疏计算;
是否进行了 TensorRT、ONNX、TVM 等部署优化。
因此,一个剪枝方法如果只报告参数量和 FLOPs,而不报告真实推理延迟,其实是不够完整的。
在实际部署场景中,Latency 往往比 FLOPs 更重要。
九、模型剪枝的一个简单例子
假设我们有一个图像分类模型,原始情况如下:
| 指标 | 原始模型 |
|---|---|
| 参数量 | 100M |
| FLOPs | 20G |
| Top-1 Accuracy | 80% |
| 推理延迟 | 50 ms |
经过剪枝后:
| 指标 | 剪枝模型 |
|---|---|
| 参数量 | 50M |
| FLOPs | 10G |
| Top-1 Accuracy | 78.8% |
| 推理延迟 | 32 ms |
这个结果说明:
参数量减少了 50%;
FLOPs 减少了 50%;
精度只下降了 1.2%;
推理延迟从 50 ms 降到 32 ms。
这种情况下,剪枝是比较成功的。
但是,如果剪枝后变成:
| 指标 | 剪枝模型 |
|---|---|
| 参数量 | 50M |
| FLOPs | 10G |
| Top-1 Accuracy | 70% |
| 推理延迟 | 48 ms |
那就说明剪枝效果并不好。虽然参数量和 FLOPs 降低了,但精度下降太多,而且真实速度几乎没有提升。因此,评价剪枝方法不能只看压缩率,还要同时看:
精度是否保持?
计算量是否下降?
实际推理是否变快?
部署是否方便?
十、模型剪枝在不同模型中的表现
不同模型结构,适合的剪枝方式也不同。
1. CNN 模型剪枝
CNN 中常见剪枝对象包括:
卷积核;
输出通道;
BatchNorm 缩放因子;
残差块;
全连接层神经元。
CNN 剪枝中,通道剪枝最常见。例如,将某一层卷积输出通道从 64 剪到 48:
Conv: 64 channels → 48 channels
这样不仅减少当前层计算量,也会减少下一层输入通道数量。因此,CNN 结构化剪枝通常能带来比较直接的计算加速。
2. Transformer 模型剪枝
Transformer 中常见剪枝对象包括:
注意力头;
FFN 中间神经元;
Transformer 层;
权重矩阵;
Token。
Transformer 剪枝比 CNN 更复杂,因为 Transformer 内部存在多头注意力、残差连接、LayerNorm 和前馈网络等结构。例如,多头注意力中某个 head 被删除后,还需要保证输出维度和后续投影矩阵能够正确匹配。
3. Vision Transformer 模型剪枝
ViT 的一个重要特点是自注意力计算复杂度与 Token 数量平方相关:
因此,ViT 剪枝中 Token 剪枝非常重要。如果能删除一部分不重要 Token,就可以显著降低注意力计算成本。例如:原始 Token 数量:196,剪枝后 Token 数量:98。理论上,注意力矩阵规模会从:,减少到:
,这对推理加速非常有吸引力。
4. 大语言模型剪枝
大语言模型剪枝主要关注:
权重稀疏;
MLP 神经元剪枝;
注意力头剪枝;
层剪枝;
结构化维度剪枝;
剪枝与量化联合压缩。
大语言模型剪枝面临一个关键问题:模型太大,完整重训练成本极高。因此,LLM 剪枝更关注训练后剪枝、免重训练剪枝、少量校准数据剪枝,以及剪枝后配合 LoRA 或蒸馏进行轻量恢复。
十一、模型剪枝的核心难点
虽然模型剪枝思想很简单,但真正做好并不容易。主要难点包括以下几个方面。
1. 如何准确判断重要性?
判断某个参数或结构是否重要,是剪枝的核心。如果重要性评分不准确,就可能误删关键结构,导致模型性能大幅下降。简单的权重幅值方法虽然方便,但并不总是可靠。因为一个权重的绝对值小,不一定代表它不重要;一个通道的响应强,也不一定代表它不可替代。更合理的方法往往需要综合考虑:
权重大小
梯度信息
激活分布
损失变化
结构冗余
层间敏感度
任务相关性
2. 如何确定每一层的剪枝率?
不同层对剪枝的敏感度不同。有些层非常冗余,可以剪掉很多;有些层非常关键,只能剪一点,甚至不能剪。如果对所有层使用相同剪枝率,比如每层都剪 50%,往往不是最优选择。更合理的方式是根据每层敏感度自适应分配剪枝率:
敏感度越高的层,剪枝率应该越低;敏感度越低的层,剪枝率可以更高。
3. 如何处理结构依赖?
结构化剪枝会改变模型结构,因此需要处理层与层之间的依赖关系。例如,在 CNN 中,如果删除前一层的某个输出通道,那么后一层对应的输入通道也必须删除。在 ResNet 中,还要考虑残差连接两边的通道维度是否一致。在 Transformer 中,删除注意力头或 MLP 维度后,也需要调整相关矩阵维度。因此,结构化剪枝不是简单地把某些权重置为 0,而是要真正重建模型结构。
4. 如何保证真实部署加速?
剪枝论文中常常报告 FLOPs 降低,但工程部署中更关心真实延迟。一个剪枝模型是否真的更快,取决于:
剪枝后的结构是否规则;
是否能被硬件高效执行;
是否减少了内存访问;
是否减少了 kernel launch 开销;
是否经过部署框架优化;
batch size 和输入尺寸是否匹配真实场景。
所以,剪枝研究不能只停留在理论计算量下降,还要关注实际部署效果。
5. 如何避免精度大幅下降?
剪枝率越高,模型越小,但精度下降风险越大。因此,剪枝通常需要配合:
微调;
知识蒸馏;
学习率调整;
渐进式剪枝;
层级敏感度分析;
校准数据;
低秩适配;
量化感知训练。
这些技术可以帮助剪枝模型恢复性能。
十二、模型剪枝和其他压缩方法的关系
模型剪枝不是孤立存在的。它经常和量化、蒸馏、低秩分解结合使用。
1. 剪枝 + 量化
剪枝减少模型结构或参数数量,量化降低每个参数的存储位宽。例如:
剪枝:100M 参数 → 50M 参数
量化:FP32 → INT8
两者结合后,模型存储可以进一步降低。
2. 剪枝 + 知识蒸馏
剪枝会导致模型性能下降,而知识蒸馏可以用大模型指导剪枝后的模型恢复性能。蒸馏损失通常可以写成:
这种方式在 Transformer 和 ViT 剪枝中非常常见。