卷积神经网络模型压缩方法介绍

1.矩阵分解法

矩阵分解法被广泛地应用于线性模型的加速以及参数的压缩上,具体方法是使用奇异值分解的方式对参数矩阵进行分解。奇异值分解有很明显的物理意义,即它可以将一个复杂矩阵用几个小矩阵相乘来表示,这些小的矩阵描述的是复杂矩阵的重要特征。例如,给定一个参数矩阵W\in R^m^{n},可以将其分解为W=USV^T。这里U\in R^{mm}V\in R^{nn}里面的向量称为左奇异向量和右奇异向量,而且向量是两两正交的。通过方阵(W^{T}W)v_{i}=\lambda _{i}v_{i}可以求得特征值\lambda _{i},这里的v_{i}为右奇异向量。再通过公式\delta _{i}=\sqrt{\lambda _{i}}u_{i}=\tfrac{1}{\delta _{i}}Mv_{i}求出奇异值\delta _{i}和左奇异向量u_{i}。选取U,V矩阵中的前k个奇异向量,以及其对应的奇异值来近似的描述参数矩阵W。于是近似矩阵\widetilde{W}可以表示为\widetilde{W}=\widetilde{U}_{m\times k}\widetilde{S}_{k\times k}\widetilde{V}_{k\times n}

SVD(奇异值分解)的逼近受S中特征值衰减的控制,SVD方法在Frobenius范数意义下是最优的,使逼近矩阵\widetilde{W}与原始W之间的最小均方误差最小。为了表示原始矩阵W,只需要将\widetilde{U}_{m\times k}\widetilde{S}_{k\times k}\widetilde{V}_{k\times n}保存起来。因此压缩率用方程表示为mn/k(m+n+1)

2.矢量量化法

2.1.k-means标量量化

K-means算法是基于距离的聚类算法,采用距离作为相似性的评价指标,即认为两个对象的距离越近,其相似度就越大。其核心思想为,通过迭代寻找k个类簇的一种划分方案,使得用这k个类簇的均值来代表相应各类样本时所得的总体误差最小。使用到参数量化编码上,如果有一参数矩阵W\in R^{m\times n},我们将其所有的标值表示为w\in R^{1\times mn}向量,对其执行kmeans聚类操作:min\sum_{i}^{mn}\sum_{j}^{k}\left \| w_{i}-c_{j} \right \|_{2}^{2},其中,wc都为标量。经过聚类操作后,w中的每个值都分配了一个簇索引,而且码本可以由簇中心c^{1\times k}表示。在预测的时候,每一个W_{ij}可以由其对应的簇中心c_{j}来表示。

对于这种方法,只需要将索引和码本作为参数来存储。给定k个中心,只需要\log _{_{2}}\left ( k \right )位来编码中心。例如,如果使用k=256个中心,每个集群索引只需要8位。假设原始w使用浮点数,压缩速率为32/\log _{_{2}}\left ( k \right )。尽管这种方法很简单,但作者的实验表明,这种方法在压缩参数方面取得了令人惊讶的良好性能。

2.2.乘积量化

乘积量化中的乘积指的是卡迪尔乘积。在数学中,两个集合XY的笛卡尓积(Cartesian product),又称值积,表示为X×Y,第一个对象是X的成员而第二个对象是Y的所有可能有序对的其中一个成员。假设集合A={a, b},集合B={0, 1, 2},则两个集合的笛卡尔积为{(a, 0), (a, 1), (a, 2), (b, 0), (b, 1), (b, 2)}。乘积量化包括特征的分组和量化,以及不同类别的卡迪尔乘积过程。

对一向量空间,k均值量化的做法就是给定类别数目K,对整个数据集进行聚类,目标函数是所有样本到类中心的距离和最小,迭代计算优化目标函数,得到k个类中心和每个样本所属的类别。而乘积量化则是将原来的向量空间分解为若干个低维向量空间的卡迪尔积,并对低维的向量空间分别做量化。这样每个向量就能由多个低维空间的量化code组合表示。

假如有一参数矩阵W\in R^{m\times n},即m个n维向量组成的矩阵,将其分解为s个子矩阵W=[W^{1},W^{2},W^{3},...,W^{s}],其中W_{i}\in W^{m\times n/s}。再对每个子矩阵用k均值聚类,得到k个类中心向量,组成子码本C^{i}\in R^{k\times n/s}c_{j}^{i}表示子码本C^{i}的第j行。对于每个子向量w_{z}^{i},我们只需要存储其相应的集群索引和代码本。集群索引需要\log _{_{2}}\left ( k \right )ms位储存,码本则需要32kn位来储存,因此压缩率为\left ( 32mn \right )/\left ( 32kn+\log _{2}\left ( k \right )ms \right )

2.3.余量量化

余量量化是另外一种结构量化方法,基本的思想是先将一组向量用k均值聚类的方法得到k个中心,然后迭代地量化其余量。例如,给定一组向量w_{i}i\in 1,....,m,先用k均值聚类的方法把它们量化成k个不同的向量min\sum_{z}^{m}\sum_{k}^{j}\left \| w_{z}-c_{j}^{1} \right \|_{2}^{2},这样就可以将w_{z}由其最近的中心c_{j}^{1}来表示。接下来在求出每一向量w_{z}与其对应的c_{j}^{1}的余量r_{z}^{1},再将这一组余量向量量化成k个不同的中心c_{j}^{2}。如此迭代t次,便可原始向量近似表示为\widehat{w}_{z}=c_{j}^{1}+c_{j}^{2}+....+c_{j}^{t}。要存储这一向量,只需存储每次迭代的码本即可。

3.深度压缩

深度压缩分为三步,模型剪枝、量化训练、哈夫曼编码,这三种方法协同合作将减少神经网络的存储需求。这种方法首先是同过学习网络中重要的连接来精简网络。其次是量化权重使网络能够共享权重。在第一步和第二步后,重新训练网络,来微调剩余的连接和量化中质心。最后采用哈夫曼编码进一步压缩模型。

3.1模型剪枝

修剪网络是用保留原始精度的方式修剪网络连接。在初始训练阶段后, 删除所有的权重低于阈值的连接。此修剪将稠密的完全连接层转换为稀疏图层。这一阶段学习网络的拓扑, 即了解哪些连接是重要的, 并删除不重要的连接。然后, 我们重新训练稀疏网络, 以便其余的连接可以补偿已删除的连接。具体步骤如下:

第一步:学习哪些连接是重要的。

第二步:修剪低权重的连接。所有权重低于阈值的连接都将从网络中删除,将稠密网络转换为稀疏网络。

第三步:重新训练网络剩余稀疏连接的最终权重。这一步很关键,因为如果修剪后的网络没有再训练, 准确性会受到显著影响。

为了进一步压缩,使用压缩稀松行格式存储剪枝后的稀松结构。压缩稀疏行格式(CSR)通过四个数组确定: values,columns, pointerB, pointerE。其中数组values:是一个实(复)数,包含矩阵A中的非0元,以行优先的形式保存;数组columns:第i个整型元素代表矩阵A中第i列;数组pointerB :第j个整型元素给出矩阵A行j中第一个非0元的位置,等价于pointerB(j) -pointerB(1)+1 ;数组pointerE:第j个整型元素给出矩阵A第j行最后一个非0元的位置,等价于pointerE(j)-pointerB(1)。例如

\begin{bmatrix} 1& 7& 0& 0\\ 0& 2& 8& 0\\ 5& 0& 3& 9\\ 0& 6& 0& 4 \end{bmatrix}可以表示为\begin{bmatrix} 0 & 2 & 4 &7 &9 \end{bmatrix}\begin{bmatrix} 0 & 1 & 1 & 2 & 0 & 2 & 3 & 1 & 3 \end{bmatrix}\begin{bmatrix} 1 & 7 & 2 & 8 & 5 & 3 & 9 & 6 & 4 \end{bmatrix}三个数组。

3.2量化训练和权重共享

量化训练可以用更少的位数代表每一权重来进一步压缩精简网络。神经网络对低精度权重值具有非常高的容忍度:极度粗略的权重值并不会降低预测精度。如图2所示,蓝色权重值最初为2.09、2.12、1.92和1.87,然后让它们共享相同的权重值2,网络的预测较精确度仍然不受影响。因此可以只存储非常少量的权重值,称之为“编码本”。并让许多其他权重共享这些相同的权重值,且只在码本中存储其索引即可。索引可以用非常少的比特数来表示。例如在下图中存在四种颜色,因此仅需要两位来表示一个权重而不用原来的32位。另一方面,编码本占用的存储空间几乎可以忽略不计。作者的实验发现,就权衡压缩比和精度而言,这种权重共享技术是优于线性量化的方法的。

对于k个中心点,只需要\log _{2}\left ( k \right )位便可以编码其索引值。对于n个连接点,每个连接点需要用b位来表示。经过量化训练后,只需要k个共享的权重值来表示。压缩率可以用公式r=\frac{nb}{nlog_{2}\left ( k \right )+kb}来表示。

量化训练使用的是k均值的方法来确定k个聚类中心,但质心初始化影响聚类的质量,影响网络的预测精度。作者研究了三种初始化方法:Forgy(随机)、基于密度和线性初始化。并得出结论,线性初始化效果最好。

3.3哈夫曼编码

霍夫曼编码使用变长编码表对源符号(如文件中的一个字母)进行编码,其中变长编码表是通过一种评估来源符号出现机率的方法得到的,出现机率高的字母使用较短的编码,反之出现机率低的则使用较长的编码,这便使编码之后的字符串的平均长度、期望值降低,从而达到无损压缩数据的目的。

1)将信源符号的概率按减小的顺序排队。

2)把两个最小的概率相加,并继续这一步骤,始终将较高的概率分支放在右边,直到最后变成概率1。

3)画出由概率1处到每个信源符号的路径,顺序记下沿路径的0和1,所得就是该符号的霍夫曼码字。   

4)将每对组合的左边一个指定为0,右边一个指定为1(或相反)。

哈夫曼编码可以用更少的位数表示权值和索引,达到压缩模型参数的目的。

猜你喜欢

转载自blog.csdn.net/weixin_37603007/article/details/82689272