Press "Enter" to skip to content

浅谈模型压缩之量化、剪枝、权重共享

深度学习模型的应用必然要面对模型压缩的问题,训练出来的原始模型直接放到服务器或终端上跑是不明智的,因为有大量的算力可以省略!

 

首先明确下模型压缩的概念,就是在尽可能不改变模型效果的情况下,减少模型的体积,使得模型在使用的时候有更快的速度。

 

01

 

业务视角去看模型压缩的意义

 

模型压缩这个概念貌似是最近两年突然火了起来,究其原因,是因为整个机器学习领域正在逐渐从理论派向工程派延伸。什幺是理论派呢?从业务的角度看,理论派就是做一些理论验证工作,通过建模证明机器学习在哪个业务能落地。而工程派指的是如何能让机器学习应用的更高效,模型压缩就是工程派的一个重要落地方向。

 

模型压缩更多地是应用到复杂的深度模型上,并且越来越受到重视,因为当模型的准确度达到一定程度后,如何用更少的硬件成本去做模型服务变的有意义。

 

举个例子,比如用深度学习变脸这样的业务。

 

 

假设在模型优化前,原始模型处理每个视频要30秒,那幺一张GPU卡一分钟只能处理2个视频。假设APP的使用峰值是1000人同时使用,那幺这家公司至少要有500张GPU卡才能满足需求,不然就会出现服务排队现象,500张卡的成本大约在3000万每年。

 

如果模型压缩技术能让模型变小许多,使得每个视频处理只需要10秒,那幺这个客户可能只需要150张卡就能满足业务需求,每年成本也能控制在1000万左右。省下的2000万,就是模型压缩技术的价值。

 

02

 

模型压缩技术有哪些

 

目前我自己了解到的的模型剪枝技术包含以下几个方向,

 

 

(模型构成)

 

 

剪枝 :深度学习模型可以看作是一个复杂树状结构,如果能减去一些对结果没什幺影响的旁枝,就可以实现模型的减小

 

量化 :模型由大量的浮点型权重组成,如果能用float32替代原有的float64表示,模型就近乎减小一倍的体积,量化也是最容易实现的一种压缩方式

 

共享权重 :有点像提取公因数,假设模型的每一层都有公用的公因数,是否可以提取出来在结果处做一次运算,而不是每一层都算一次

 

 

接下来会针对以上三点逐个介绍。

 

03

 

模型剪枝

 

模型的构成是由许多浮点型的神经元相连接,每一层根据神经元的权重将信息向下传递。但是有一些神经元的权重非常小,这类神经元对整个模型的加载的信息的影响也就微乎其微。如果可以把这些权重较小的神经元删减掉,既减少了模型大小,也不会对模型的效果带来大的影响。

 

简单理解的话如下图所示:

 

 

每一层把数值小的神经元去掉,但是究竟剪枝粒度维持到多大是很有讲究的,比如可以把每层最小的5个减掉,也可能只剪3个,或者每层有每层不同的策略,也可以用L1/L2正则的方式去做。

 

剪多了,模型精度影响会比较大,剪少了没有效果。所以这里面需要大量的尝试和迭代,在实践中,剪枝是一个迭代的过程,这通常叫做「迭代式剪枝」(Iterative Pruning):修剪-训练-重复(Prune / Train / Repeat)。

 

既然有大量的迭代验证工作,是否可以引入AutoML机制,可以通过NAS(神经网络搜索)的方式探索出剪枝候选集,然后自动的剪枝-》验证-》迭代。从NAS的角度去实现还是有许多工作可以去做,也是一个热点话题。

 

0 4

 

模型量化

 

模型的精度量化并不是简单的将高精度的权重用低精度权重表示就好了,这里面涉及到许多适配硬件的因素。先来看下神经元权重是如何在计算机里表示的。 目前DL中大部分都是用32bit float类型进行计算的,bit位数的多少直接限制了数据类型能够表达的数据范围,比如float 32的数据是由1bit表示符号,8bit表示整数部,23位表示分数部组成(计算机课都学过的)。

 

 

用更低位的数值类型意味着更小的数据表示范围和更稀疏的数值,量化的时候就会造成数值精度损失。比如要把float数值量化 到int类型,那幺首先小数部分会损失,而那些超过int类型能够表达的范围的值也会被压缩到int能够表达的最大或最小值。

 

 

所以,如果要压缩模型,从float32压缩到多少变的关键,目前主流的方式是压缩到int8。压缩到int8意味着内存的节省,节约了3/4,同时也提升了计算效率,因为在GPU这样的硬件上,低位的浮点计算速度会远远高于高位浮点计算速度。

 

 

So,why int 8?有相关的人士分析过,从概率分布角度去看,int8的字符长度可以较完整的覆盖大部分的模型权重值。float 32到int8的转变,只需要一个系数乘积将原有的小数部分变为整数。int 8量化效果在许多论文上可以看到,是目前最主流的模型压缩方式。

 

0 5

 

模型共享权重

 

共享权重的概念指的是模型在构建的过程中是否有些局部的信息在全局是多次出现并重复使用的,举一个卷积神经网络的例子。当CNN模型在识别以下这个图像的时候,

 

 

需要卷积核去全图扫描这个图像,找出每个边缘的特点,但是这种对称图像一定存在一些形状的重复性,比如下图我框出的这些结构。

 

 

这些重复结构意味着卷积核在计算权重的时候会有部分权重的相似性,这些相似性是全局可共享的。那幺如果可以通过聚类的方式挖掘出这些可以共享的权重系数,并且以类别的方式让它们共享一些权重,就可以实现模型的压缩。

 

下图表示的就是卷积核中的部分权重是有共享关系的,可以将他们分为4个种类,然后针对类别去更新权值即可。

 

 

0 6

 

总结

 

因为业务需要,最近学习和总结了这篇文章,写的很简单,有不清晰或者不正确的地方请指正。另外,从根客户接触的情况看,目前模型优化还没有特别好的自动化工具,很多方法应用到业务中都会造成大规模的模型精度损失,所以目前很多模型压缩工作需要大量人力介入和反复调试,希望日后有真正工业级别的压缩工具诞生。

 

参考:

 

 

https://blog.csdn.net/malvas/article/details/8664778

 

https://www.cnblogs.com/arkenstone/p/10856466.html

 

https://blog.csdn.net/weixin_38740463/article/details/90181264

 

https://zhuanlan.zhihu.com/p/97198052

 

https://www.zhihu.com/search?type=content&q=%E6%A8%A1%E5%9E%8B%E5%8E%8B%E7%BC%A9

 

https://baijiahao.baidu.com/s?id=1641186698550736256&wfr=spider&for=pc

Be First to Comment

发表回复

您的电子邮箱地址不会被公开。 必填项已用*标注