模型量化¶
首先我们介绍一下 Paddle 支持的模型量化方法,让大家有一个整体的认识。
Paddle 模型量化包含三种量化方法,分别是动态离线量化方法、静态离线量化方法和量化训练方法。
下图展示了如何选择模型量化方法。
下图综合对比了模型量化方法的使用条件、易用性、精度损失和预期收益。
大家可以根据不同情况选用不同的量化方法,有几点着重注意:
动态离线量化方法主要用于减小模型体积
静态离线量化方法和量化训练方法既可以减小模型体积,也可以加快性能,性能加速基本相同
静态离线量化方法比量化训练方法更加简单,一般建议首先使用静态离线量化方法,如果量化模型精度损失较大,再尝试使用量化训练方法。
本章节主要介绍使用 PaddleSlim 量化训练方法产出的量化模型,使用 Paddle Lite 加载量化模型进行推理部署,
量化训练¶
1 简介¶
量化训练是使用较多训练数据,对训练好的预测模型进行量化。该方法使用模拟量化的思想,在训练阶段更新权重,实现减小量化误差。
使用条件:
有预训练模型
有较多训练数据(通常大于5000)
使用步骤:
产出量化模型:使用 PaddlePaddle 调用量化训练接口,产出量化模型
量化模型预测:使用 Paddle Lite 加载量化模型进行预测推理
优点:
减小计算量、降低计算内存、减小模型大小
模型精度受量化影响小
缺点:
使用条件较苛刻,使用门槛稍高
建议首先使用“静态离线量化”方法对模型进行量化,然后使用使用量化模型进行预测。如果该量化模型的精度达不到要求,再使用“量化训练”方法。
2 产出量化模型¶
目前,PaddleSlim 的量化训练主要针对卷积层和全连接层,对应算子是 conv2d、depthwise_conv2d、conv2d_tranpose 和 mul。Paddle Lite 支持运行 PaddleSlim 量化训练产出的模型,可以进一步加快模型在移动端的执行速度。
温馨提示:如果您是初次接触 PaddlePaddle 框架,建议首先学习使用文档。
使用 PaddleSlim 模型压缩工具训练量化模型,请参考文档:
3 使用 Paddle Lite 运行量化模型推理¶
首先,使用 Paddle Lite 提供的模型转换工具(model_optimize_tool)将量化模型转换成移动端预测的模型,然后加载转换后的模型进行预测部署。
3.1 模型转换¶
参考模型转换准备模型转换工具,建议从 Release 页面下载。
参考模型转换使用模型转换工具,参数按照实际情况设置。比如在安卓手机ARM端进行预测,模型转换的命令为:
./OPT --model_dir=./mobilenet_v1_quant \
--optimize_out_type=naive_buffer \
--optimize_out=mobilenet_v1_quant_opt \
--valid_targets=arm
3.2 量化模型预测¶
和 FP32 模型一样,转换后的量化模型可以在 Android/IOS APP 中加载预测,建议参考C++ Demo、Java Demo、Android/IOS Demo。
FAQ¶
问题:Compiled with WITH_GPU, but no GPU found in runtime
解答:检查本机是否支持 GPU 训练,如果不支持请使用 CPU 训练。如果在 docker 进行 GPU 训练,请使用 nvidia_docker 启动容器。
问题:Inufficient GPU memory to allocation. at [/paddle/paddle/fluid/platform/gpu_info.cc:262]
解答:正确设置 run.sh 脚本中CUDA_VISIBLE_DEVICES
,确保显卡剩余内存大于需要内存。
离线量化-动态离线量化¶
本部分首先简单介绍动态离线量化,然后说明产出量化模型,最后阐述量化模型预测。
1 简介¶
动态离线量化,将模型中特定 OP 的权重从 FP32 类型量化成 INT8/16 类型。
该量化模型有两种预测方式:
第一种是反量化预测方式,即是首先将 INT8/16 类型的权重反量化成 FP32 类型,然后再使用 FP32 浮运算运算进行预测;
第二种量化预测方式,即是预测中动态计算量化 OP 输入的量化信息,基于量化的输入和权重进行 INT8 整形运算。
注意:目前 Paddle Lite 仅支持第一种反量化预测方式。
使用条件:
有训练好的预测模型
使用步骤:
产出量化模型:使用 PaddlePaddle 调用动态离线量化离线量化接口,产出量化模型
量化模型预测:使用 Paddle Lite 加载量化模型进行预测推理
优点:
权重量化成 INT16 类型,模型精度不受影响,模型大小为原始的1/2
权重量化成 INT8 类型,模型精度会受到影响,模型大小为原始的1/4
缺点:
目前只支持反量化预测方式,主要可以减小模型大小,对特定加载权重费时的模型可以起到一定加速效果
和静态离线量化相比,目前 Paddle Lite 只支持反量化预测方式,对于预测过程的加速有限;但是动态离线量化不需要训练数据即可完成量化,达到减小模型大小的目的。
2 产出量化模型¶
Paddle Lite OPT 工具和 PaddleSlim 都提供了动态离线量化功能,两者原理相似,都可以产出动态离线量化的模型。
2.1 使用 Paddle Lite OPT 产出量化模型¶
Paddle Lite OPT 工具将动态离线量化功能集成到模型转换中,使用简便,只需要设置对应参数,就可以产出优化后的量化模型。
2.1.2 准备模型¶
准备已经训练好的 FP32 预测模型,即 save_inference_model()
保存的模型。
2.1.3 产出量化模型¶
参考 OPT 文档中使用 OPT 工具的方法,在模型优化中启用动态离线量化方法产出优化后的量化模型。
如果是使用可执行文件 OPT 工具,参考直接下载并执行 OPT 可执行工具。
设置常规模型优化的参数后,可以通过 --quant_model
设置是否使用 OPT 中的动态离线量化功能,通过 --quant_type
参数指定 OPT 中动态离线量化功能的量化类型,可以设置为 QUANT_INT8 和 QUANT_INT16 ,即分别量化为 int8 和 int16 。量化为 int8 对模型精度有一点影响,模型体积大概减小4倍。量化为 int16 对模型精度基本没有影响,模型体积大概减小2倍。
举例如下:
./OPT \
--model_dir=<model_param_dir> \
--model_file=<model_path> \
--param_file=<param_path> \
--optimize_out_type=naive_buffer \
--optimize_out= <output_optimize_model_dir>\
--quant_model=true \
--quant_type=QUANT_INT16
如果使用 python 版本 OPT 工具,请参考安装 python 版本 OPT 后,使用终端命令和安装 python 版本 OPT 后,使用 python 脚本,都有介绍设置动态离线量化的参数和方法。
2.2 使用 PaddleSlim 产出量化模型¶
大家可以使用 PaddleSlim 调用动态离线量化接口,得到量化模型。
2.2.2 准备模型¶
准备已经训练好的 FP32 预测模型,即 save_inference_model()
保存的模型。
2.2.3 调用动态离线量化¶
对于调用动态离线量化,首先给出一个例子。
from paddleslim.quant import quant_post_dynamic
model_dir = path/to/fp32_model_params
save_model_dir = path/to/save_model_path
quant_post_dynamic(model_dir=model_dir,
save_model_dir=save_model_dir,
weight_bits=8,
quantizable_op_type=['conv2d', 'mul'],
weight_quantize_type="channel_wise_abs_max",
generate_test_model=False)
执行完成后,可以在 save_model_dir/quantized_model
目录下得到量化模型。
3 量化模型预测¶
目前,对于动态离线量化产出的量化模型,只能使用 Paddle Lite 进行预测部署。
很简单,首先使用 Paddle Lite 提供的模型转换工具(OPT)将量化模型转换成移动端预测的模型,然后加载转换后的模型进行预测部署。
注意,Paddle Lite 2.3 版本才支持动态离线量化产出的量化,所以转换工具和预测库必须是2.3及之后的版本。
3.1 模型转换¶
参考模型转换准备模型转换工具,建议从 Release 页面下载。
参考模型转换使用模型转换工具。 比如在安卓手机 ARM 端进行预测,模型转换的命令为:
./OPT --model_dir=./mobilenet_v1_quant \
--optimize_out_type=naive_buffer \
--optimize_out=mobilenet_v1_quant_opt \
--valid_targets=arm
3.2 量化模型预测¶
和 FP32 模型一样,转换后的量化模型可以在 Android/IOS APP 中加载预测,建议参考 C++ Demo、Java Demo、Android/IOS Demo。
离线量化-静态离线量化¶
1 简介¶
静态离线量化,使用少量校准数据计算量化因子,可以快速得到量化模型。使用该量化模型进行预测,可以减少计算量、降低计算内存、减小模型大小。
静态离线量化中,有两种计算量化因子的方法,非饱和量化方法和饱和量化方法。非饱和量化方法计算整个 Tensor 的绝对值最大值abs_max
,将其映射为127。饱和量化方法使用 KL 散度计算一个合适的阈值T
(0<T<mab_max
),将其映射为127。一般而言,待量化 Op 的权重采用非饱和量化方法,待量化 Op 的激活(输入和输出)采用饱和量化方法 。
使用条件:
有训练好的预测模型
有少量校准数据,比如100~500张图片
使用步骤:
产出量化模型:使用 PaddleSlim 调用静态离线量化接口,产出量化模型
量化模型预测:使用 Paddle Lite 加载量化模型进行预测推理
优点:
减小计算量、降低计算内存、减小模型大小
不需要大量训练数据
快速产出量化模型,简单易用
缺点:
对少部分的模型,尤其是计算量小、精简的模型,量化后精度可能会受到影响
2 产出量化模型¶
大家可以使用 PaddleSlim 调用静态离线量化接口,得到量化模型。
2.2 准备模型和校准数据¶
准备已经训练好的 FP32 预测模型,即 save_inference_model()
保存的模型。
准备校准数据集,校准数据集应该是测试集/训练集中随机挑选的一部分,量化因子才会更加准确。对常见的视觉模型,建议校准数据的数量为100~500张图片。
2.3 配置校准数据生成器¶
静态离线量化内部使用异步数据读取的方式读取校准数据,大家只需要根据模型的输入,配置读取数据的 sample_generator。sample_generator 是 Python 生成器,必须每次返回单个样本数据,会用作DataLoader.set_sample_generator()
的数据源。
建议参考异步数据读取文档和本文示例,学习如何配置校准数据生成器。
2.4 调用静态离线量化¶
对于调用静态离线量化,首先给出一个例子,让大家有个直观了解。
import paddle.fluid as fluid
from paddleslim.quant import quant_post_static
exe = fluid.Executor(fluid.CPUPlace())
model_dir = path/to/fp32_model_params
## set model_filename as None when the filename is __model__,
## otherwise set it as the real filename
model_filename = None
## set params_filename as None when all parameters were saved in
## separate files, otherwise set it as the real filename
params_filename = None
save_model_path = path/to/save_model_path
## prepare the sample generator according to the model, and the
## sample generator must return a sample every time. The reference
## document: https://www.paddlepaddle.org.cn/documentation/docs/zh
## /user_guides/howto/prepare_data/use_py_reader.html
sample_generator = your_sample_generator
batch_size = 10
batch_nums = 10
algo = "KL"
quantizable_op_type = ["conv2d", "depthwise_conv2d", "mul"]
quant_post_static(executor=exe,
model_dir=model_dir,
model_filename=model_filename,
params_filename=params_filename,
quantize_model_path=save_model_path,
sample_generator=sample_generator,
batch_size=batch_size,
batch_nums=batch_nums,
algo=algo,
quantizable_op_type=quantizable_op_type)
API 接口请参考文档。
Demo 请参考文档。
3 量化模型预测¶
首先,使用PaddleLite提供的模型转换工具(model_optimize_tool)将量化模型转换成移动端预测的模型,然后加载转换后的模型进行预测部署。
3.1 模型转换¶
参考模型转换准备模型转换工具,建议从 Release 页面下载。
参考模型转换使用模型转换工具,参数按照实际情况设置。比如在安卓手机 ARM 端进行预测,模型转换的命令为:
./OPT --model_dir=./mobilenet_v1_quant \
--optimize_out_type=naive_buffer \
--optimize_out=mobilenet_v1_quant_opt \
--valid_targets=arm
3.2 量化模型预测¶
和 FP32 模型一样,转换后的量化模型可以在 Android/IOS APP 中加载预测,建议参考C++ Demo、Java Demo、Android/IOS Demo。