开源一年,阿里轻量级AI推理引擎MNN 1.0.0正式发布

在经过充分的行业调研后,阿里淘系技术部认为当时的推理引擎如TFLite不足以满足手机淘宝这样一个亿级用户与日活的超级App。

于是,他们从零开始自己搭建了属于阿里巴巴的推理引擎MNN。1年前,MNN在Github上开源,截止目前获得了3.9k Stars。

MNN比其他的推理引擎更快更轻量,更符合手机淘宝这样庞大、复杂的生产部署环境。今年3月份,基于MNN的引擎设计与优化理念,阿里在MLSys 2020上发表了论文,并进行了oral presentation。

开源1年以来,基于阿里内外的用户反馈和业务推动,他们称,MNN在许多方面都取得了长足的进步:

  • 在阿里巴巴集团内部得到广泛推广,成为了端上推理引擎的事实标准,覆盖了如手机淘宝、手机天猫、优酷、钉钉、闲鱼等20多个App。

  • 新添了模型训练的支持,从此MNN不再是单纯的推理引擎,而是具有推理+训练能力的深度学习引擎。基于MNN的训练能力,可以进行Quantization Aware Training (QAT)。在MobileNet上,MNN量化训练之后的模型准确率几乎不降。

  • 持续投资于异构硬件后端的优化,尤其是利用ARMv8.2指令集,获得了两倍的性能提升。

  • 进一步完善Python工具链,累计新增超过150个接口。

  • 开源了应用层开箱即用的解决方案MNNKit,包含了人脸跟踪与检测、人像分割、手势识别场景的解决方案。

近日,MNN发布了1.0.0正式版本。相较于0.2.2版本,1.0.0版本的主要升级在于:模型训练、异构性能和Python工具链。

 

模型训练

模型构建

MNN支持使用 Express (表达式)接口来构建模型,模型的构建、训练和保存具体可以参考说明文档。

VARP x = inputs[0];x      = conv1->forward(x);x      = _MaxPool(x, {2, 2}, {2, 2});x      = conv2->forward(x);x      = _MaxPool(x, {2, 2}, {2, 2});x      = _Convert(x, NCHW);x      = _Reshape(x, {0, -1});x      = ip1->forward(x);x      = _Relu(x);x      = dropout->forward(x);x      = ip2->forward(x);x      = _Softmax(x, 1);return {x};

据介绍,以MNIST数据集 + Lenet网络为例,一个epoch 60000张图片,一般可达到97-98%的准确率。性能上,同款MBP上,MNN比PyTorch和Caffe都有明显优势;而手机上,MNN也达到了完全可用的性能水准。

量化训练

模型量化既可以降低模型大小,又可以利用硬件特性提升推理性能,可谓业务应用必备之选。但美中不足之处在于,模型量化会带来一定的精度损失 —— 对于精度攸关的项目,就难免要做出艰难的选择。

                                                 

为此,MNN借助自身模型训练能力,实现了模型训练量化,具体实现可以参考说明文档。精度和压缩率方面,以MobileNet V2为例说明:

模型

类型

准确率

模型大小

原始模型

float32

72.324%

13M

MNN 训练量化模型

symm int8

72.456%

3.5M

TensorFlow 训练量化模型

symm int8

71.1%

3.5M

注1:训练和验证均采用ImageNet数据集。训练采用32为batch size,执行100个迭代,即,使用了3200张图片进行训练;精度验证则使用了50000张图片。

注2:原始模型为TensorFlow官方模型,官方准确率为71.8%,但因预处理代码上有细微差别,我们测试原始模型的准确率结果稍高于官方;

 

可以看出,在实现了73%模型尺寸压缩的情况下,量化模型的精度甚至要稍高于原始模型。

 

异构性能

x86

在x86上,我们重点优化了矩阵乘法。在分析过AVX和Arm向量乘指令差异后,我们修改了AVX下的权重矩阵布局,降低了I/O布局,以充分利用CPU算力。

 

此外,我们允许在支持FMA扩展的设备上,启用扩展,将乘法和加法合为一条指令,以进一步降低指令耗时。

当前,FMA扩展的启用开关还放置在CMakeLists.txt中,后续会在运行时判别。

综合两项优化,x86上有30%左右的性能优化。

 

ARM64

在ARM64上,他们面向中低端设备,调整了矩阵乘法的分块策略,矩阵中每个元素的均摊I/O降低了22%;同时,将数据对齐从32字节调整为64字节,与ARM架构CPU下场景的L1 cacheline匹配;最后,优化了缓存预取。优化结果如下:

ARMv8.2

ARM在「Bringing Armv8.2 Instructions to Android Runtime」一文中,列举了可以在Android运行时中应用的ARMv8.2新特性。其中,FP16 extensions和Dot Product可以分别应用于浮点计算加速和量化计算加速。

 

FP16 extensions

                             

亦记作asimdhp(Advanced SIMD Half Precision),是ARMv8.2架构的可选扩展。asimdhp可用时,可以使用相关SIMD指令实现float16的读写计算。float16将float32所需的位数降低了一半,因此在SIMD下,可以实现两倍的并发吞吐,从而优化性能。为此,我们在卷积中,采用[N,C/8,H,W,8]的数据布局,新增了部分卷积实现,效果如下:

精度上几乎没有下降,但是性能足足提升了一倍。搭配上MNN转换工具的--fp16输出选项,模型大小还能减小一半。一箭双雕。

 

Dot Product

         

亦记作asimddp(Advanced SIMD Dot Product),是ARMv8.2架构的可选扩展。asimddp可用时,可以使用SDOT/UDOT指令实现int8/uint8的点积计算。SDOT/UDOT指令如上图所示,一次可以处理两个4x4 int8/uint8数据乘,并累加到4x1的int32/uint32的寄存器上。这样强大的硬件加速指令,还是双发射的。

实战表现效果也非常明显,在原先int8无法发挥效用的设备上,ARMv8.2也成功实现了耗时减半。

 

Python工具链

2019年的绿盟开发者大会上,我们发布了MNN的Python前端和Python版的转换、量化、可视化工具。而今,Python又增加了对MNN Express (表达式)、模型训练的封装,累计新增超过150个接口。

依然是前文的Express构图,使用Python改写的版本如下:

class Net(nn.Module):    """construct a lenet 5 model"""    def __init__(self):        super(Net, self).__init__()        self.conv1 = nn.conv(1, 20, [5, 5])        self.conv2 = nn.conv(20, 50, [5, 5])        self.fc1 = nn.linear(800, 500)        self.fc2 = nn.linear(500, 10)
    def forward(self, x):        x = F.relu(self.conv1(x))        x = F.max_pool(x, [2, 2], [2, 2])        x = F.relu(self.conv2(x))        x = F.max_pool(x, [2, 2], [2, 2])        x = F.convert(x, F.NCHW)        x = F.reshape(x, [0, -1])        x = F.relu(self.fc1(x))        x = self.fc2(x)        x = F.softmax(x, 1)        return x

 

注:目前Python Express API处于BETA阶段。阿里会根据社区和内部的反馈持续改进Python API,包含进行backward incompatible的改动。

推荐阅读

  • 你点的每个“在看”,我都认真当成了AI

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值