神经网络模型压缩技术

一、当前的模型压缩方法主要有6类:网络剪枝、参数共享、量化、网络分解、网络蒸馏、紧凑网络设计。

1.网络剪枝

在网络训练过程中寻求一种评判机制,剔除掉不重要的连接、节点甚至卷积核,达到精简网络结构的目的。很多实验表明卷积层到全连接层存在大量冗余参数,大多是神经元被激活后的输出值区域为0,即使将这些神经元剔除也能够表达出模型特征

2.参数共享

主要思想是让网络中多个参数共享同一值,但具体实现方式不同。如利用K-means聚类、低秩分解、权重采样等。但可能会因为过分追求模型压缩比导致模型精度的下降。

3.量化

量化:降低权重所需要的比特数来压缩原始网络,主要包括低精度和重编码两类方法。低精度就是用更低位数的浮点数或整型数表示权重参数进行训练、测试或存储;重编码则是对原始数据进行重编码,采用更少的位数对原有数据进行表示,代表有二值化权重/二值化神经网络。

4.网络分解

网络分解主要将矩阵二维张量进行奇异值分解。

5.网络蒸馏

网络蒸馏又叫知识蒸馏,目的是将教师模型学到的知识转化到学生模型中。比如将教师模型的softmax层作为学生模型的监督;但有些任务中直接使用教师模型的输出对学生模型进行监督会比较困难,因此可参考将教师模型的中间层输出作为对学生模型的中级监督信息等。

6.轻量级网络设计

大致分为两大方向:紧凑卷积结构和网络结构搜索。

紧凑卷积结构:SqueezeNet, MobileNet,ShffleNet等轻量级网络系列,致力于设计出更加精简有效的网络;

网络结构搜索:Neural Architecture Search, NAS神经网络结构搜索的不同之处在于,传统的网络模型及参数均为人工设计,往往导致设计出的模型并非最优。NAS则通过搜索方法寻找最优的神经网络架构,一旦此类方法成熟,将很适合工业界应用。

二、剪枝

首先按照剪枝时间可以分为:

训练中剪枝损失函数添加约束项诱导网络稀疏化,无需重训练

训练后剪枝剔除网络中相对冗余、不重要的部分

按照剪枝粒度可以分为:

结构化剪枝对整个卷积核或者通道进行剪枝从而没有破坏原有的卷积结构,更适合在通用的硬件上使用;

(1)通道剪枝

(2)卷积剪枝

(3)Layer剪枝

非结构化剪枝:单个权重剪枝。非结构化剪枝将原本稠密的参数矩阵裁剪为稀疏的参数矩阵,一般矩阵大小不变,其效果类似于参数正则化。由于目前大部分平台不支持稀疏矩阵的计算。

按照剪枝方式可以分为:

软剪枝(SFP):在每个epoch后将需要剪枝的卷积核保留,只是将其参数置为0,依旧参与下一轮的迭代更新,在所有epoch循环结束后进行权重修剪。

硬剪枝(HFP)在每个epoch后会将卷积核直接剪掉,被剪掉的卷积核在下一个epoch中不会再出现

其中,软剪枝主要步骤如下:

1filter selection采用L2-norm(作为importance衡量准则)以及预先定义的剪枝率Pi,选择出一些不重要的filters;

2. filter pruning:在每个epoch训练开始之前,在全局层面将不重要的filters置零,并允许置0的filters在当前epoch训练期间接受参数更新

3. reconstruction:通过反向传播更新所有filters,能够让pruned model按照与原始模型相同的容量接受参数更新。显然,置0的filters对应的前向输出将趋于零,导致下一层input filters的梯度也趋于零,经梯度反传之后,对应的参数更新幅度也会变得很小,而重要filters仍然接受正常的参数更新,从而达到理想的正则化效果;

4. obtaining compact model:最终正则化、收敛以后,通过裁减掉zero filters可以获得结构紧凑的网络模型,同时达到理想的压缩与加速效果;

通过SFP引申出ASFP和FPGM剪枝。其中,ASFP是在软剪枝的基础上,渐进地修剪网络。在训练过程中,先删除几个少量的滤波器,然后随着迭代的进行渐进的删除更多的滤波器。在渐进剪枝的情况下,训练集的信息会逐渐集中在剩余的滤波器中,从而使得后续的训练和剪枝过程更加稳定。ASFP与SFP的区别在于每次迭代时,滤波器的剪枝率会随着迭代次数的增加而由低到高的变化,直到增加到和SFP一致的裁剪率为止。FPGM与SFP不同的是选取几何中位数附近的卷积核进行剪枝。几何中位数是对于欧几里得空间的点的中心的一个估计。我们认为滤波器也是欧氏空间中的点,于是我们可以根据计算GM来得到这些滤波器的“中心”,也就是他们的共同性质。如果某个滤波器接近于这个GM,可以认为这个滤波器的信息跟其他滤波器重合,甚至是冗余的,于是我们可以去掉这个滤波器而不对网络产生大的影响。去掉它后,它的功能可以被其他滤波器代替。

三、量化

按照聚类中心是否均匀可以分为:

线性量化:线性量化采用均匀分布的聚类中心,原始数据跟量化后的数据存在一个简单的线性变换关系。而卷积、全连接本身也只是简单的线性计算,因此在线性量化中可以直接用量化后的数据进行直接计算,不仅可以压缩模型文件的大小,还能带来明显的速度提升。

非线性量化:采用不规则的聚类中心,通过KMEANS对浮点权重进行量化,并在训练过程中逐步修正聚类中心——不规则的聚类中心往往能在相同的比特数下取得更小的量化误差,但由于必须先查表取得原始数据再进行计算,所以对计算的加速没有任何帮助,这种方法更多是用来压缩模型文件大小。

其中,线性量化过程可以用下式表示:

r=Round(S(qZ))

其中,

q 是float32的原始值;

Z 是float32的偏移量,也可以量化为int32;

S 是float32的缩放因子;

Round()是四舍五入近似取整的数学函数,除了四舍五入,向上、向下取整也是可以的;

r是量化后的一个整数值。

而我们需要做的,就是确定合适的 S 和 Z。

根据参数Z是否为零可以将线性量化分为:

对称量化:

神经网络模型压缩技术_第1张图片

在对称量化中,r是用有符号的整型数值来表示的,此时 Z = 0,且 q = 0 时恰好有r=0。比如简单地取,

神经网络模型压缩技术_第2张图片 

其中,

n 是用来表示该数值的位宽,

x是数据集的总体样本。

对称量化比较简单,不仅实现简单,而且由于Z = 0运算也变得非常简单

非对称量化:

神经网络模型压缩技术_第3张图片

 神经网络模型压缩技术_第4张图片

非对称量化比较灵活,通常 r是用无符号的整型数值来表示,此时 Z ≠ 0。

按照量化的粒度可以分为:

逐层量化:以一个层为单位,整个layer的权重共用一组缩放因子S和偏移量Z

逐组量化:以组为单位,每个group使用一组S和Z

逐通道量化:以通道为单位,每个channel单独使用一组S和Z

当 group=1 时,逐组量化与逐层量化等价;

当 group=num filters时,逐组量化逐通道量化等价。

按照需要量化的参数可以分为:

权重量化仅需要对网络中的权重执行量化操作。由于网络的权重一般都保存下来了,因而我们可以提前根据权重获得相应的量化参数S和Z,而不需要额外的校准数据集。一般来说,推理过程中,权重值的数量远小于激活值,仅仅对权重执行量化的方法能带来的压缩力度和加速效果都一般。

权重激活量化不仅对网络中的权重进行量化,还对激活值进行量化。由于激活层的范围通常不容易提前获得,因而需要在网络推理的过程中进行计算或者根据模型进行大致的预测。

PACT量化(Parameterized clipping activation)提出在量化激活值之前去掉一些离群点来降低模型量化带来的精度损失。activation的量化可能引起的误差很大(相较于weight基本在 0到1范围内,activation的值的范围是无限大的,这是RELU的结果),所以提出截断式RELU的激活函数。该截断的上界,即α 是可学习的参数,这保证了每层能够通过训练学习到不一样的量化范围,最大程度降低量化带来的舍入误差。

神经网络模型压缩技术_第5张图片

如上图,PACT解决问题的方法是,不断裁剪激活值范围,使得激活值分布收窄,从而降低量化映射损失。

PACT通过对激活数值做裁剪,从而减少激活分布中的离群点,使量化模型能够得到一个更合理的量化scale,降低量化损失。

PACT的公式如下所示:

神经网络模型压缩技术_第6张图片 

PACT量化改进:

改进后公式如下:

神经网络模型压缩技术_第7张图片

优势:在激活值和待量化的OP(卷积,全连接等)之间插入这个PACT预处理,不只对大于0的分布进行截断,同时也对小于0的部分做同样的限制,从而更好地得到待量化的范围,降低量化损失。同时,截断阈值是一个可训练的参数,在量化训练过程中,模型会自动的找到一个合理的截断阈值,从而进一步降低量化精度损失。

按照激活值的量化方式可以分为:

在线量化:指激活值的S和Z在实际推断过程中根据实际的激活值动态计算

离线量化:指提前确定好激活值的S和Z,需要小批量的一些校准数据集支持。由于不需要动态计算量化参数,通常离线量化的推理速度更快些

通常使用以下的三种方法来确定相关的量化参数:

指数平滑法:将校准数据集送入模型,收集每个量化层的输出特征图,计算每个batch的S和Z值,并通过指数平滑法来更新S和Z值。

直方图截断法:在计算量化参数Z和S的过程中,由于有的特征图会出现偏离较远的奇异值,导致max非常大,所以可以通过直方图截取的形式,比如抛弃最大的前1%数据,以前1%分界点的数值作为max计算量化参数。

KL散度校准法:通过计算KL散度来评估量化前后的两个分布之间存在的差异,搜索并选取KL散度最小的量化参数Z和S作为最终的结果。Tensor RT中就采用了这种方法。

按照是否需要再训练可以分为:

训练后量化(PTQ):不需要再训练,因此是一种轻量级的量化方法。在大多数情况下,训练后量化足以实现接近FP32性能的INT8量化。然而,它也有局限性,特别是针对激活更低位的量化,如4bit2bit

训练时量化(QAT):量化感知训练,可以获得更高精度的低位量化,但是需要修改训练代码,并且反向传播过程对梯度的量化误差很大,容易导致不收敛。

你可能感兴趣的:(神经网络压缩,神经网络,深度学习)