由于BERT参数众多,模型庞大,训练与推理速度较慢,在一些实时性要求较高应用场景无法满足需求,最近开始探索BERT轻量化部署
BERT轻量化的方式:
- 低精度量化。在模型训练和推理中使用低精度(FP16甚至INT8、二值网络)表示取代原有精度(FP32)表示。
- 模型裁剪和剪枝。减少模型层数和参数规模。
- 模型蒸馏。通过知识蒸馏方法[22]基于原始BERT模型蒸馏出符合上线要求的小模型。
本文主要分享下BERT的剪枝实践,代码来源于Rasa,对剪枝部分代码进行了剥离和修改,然后进行试验,模型是变小了,但是推理时间反而增加(囧),Rasa的代码还在研究中,先放一部分试验结果。
剪枝的方式两种:
- neuron pruning
- weigth pruning
实验结果:
结论就是剪枝完,并没啥用??继续看下代码吧。哪位尝试过rasa-bert剪枝代码的同学,麻烦指导下。
部分试验过程:
Variable: bert/encoder/layer_9/intermediate/dense/mask:0
Shape: (768, 3072)
Element sparsity: 50.0%
Column sparsity: 0.0% (3072/3072)
Variable: bert/encoder/layer_9/output/dense/mask:0
Shape: (3072, 768)
Element sparsity: 50.0%
Column sparsity: 0.0% (768/768)
Variable: bert/pooler/dense/mask:0
Shape: (768, 768)
Element sparsity: 50.0%
Column sparsity: 0.0% (768/768)
###########################################################################
Overall:
Element sparsity: 50.0%
Column sparsity: 0.0%
Variable: bert/encoder/layer_9/attention/self/query/mask:0
Shape: (768, 768)
Element sparsity: 63.8%
Column sparsity: 63.8% (278/768)
Variable: bert/encoder/layer_9/attention/self/value/mask:0
Shape: (768, 768)
Element sparsity: 29.3%
Column sparsity: 29.3% (543/768)
Variable: bert/encoder/layer_9/intermediate/dense/mask:0
Shape: (768, 3072)
Element sparsity: 76.6%
Column sparsity: 76.6% (720/3072)
Variable: bert/encoder/layer_9/output/dense/mask:0
Shape: (3072, 768)
Element sparsity: 16.3%
Column sparsity: 16.3% (643/768)
Variable: bert/pooler/dense/mask:0
Shape: (768, 768)
Element sparsity: 4.7%
Column sparsity: 4.7% (732/768)
###########################################################################
Overall:
Element sparsity: 41.1%
Column sparsity: 50.0%
补充下rasa的代码位置:https://github.com/RasaHQ/rasa/tree/nlu_lstm-compressing_transformers/rasa/nlu/classifiers
文章: Learn how to make BERT smaller and faster | The Rasa Blog | Rasa
抽离出来后,需要对代码进行修改,才能跑通。