From 725e9cf70f1eb0ee0aa6a672aa01afb1c789b22a Mon Sep 17 00:00:00 2001 From: Megvii Engine Team Date: Wed, 1 Jul 2020 17:02:26 +0800 Subject: [PATCH] fix(advanced): fix deployment doc GitOrigin-RevId: e703805a8cad9d01ca9ba3f489e57fbb0a7ba2f4 --- source/advanced/deployment.rst | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/source/advanced/deployment.rst b/source/advanced/deployment.rst index 030a75f..079809c 100644 --- a/source/advanced/deployment.rst +++ b/source/advanced/deployment.rst @@ -35,11 +35,11 @@ MegEngine 的一大核心优势是“训练推理一体化”,其中“训练 pred_fun.trace(data, net=xor_net) # 使用 trace 类的 dump 接口进行部署 - pred_fun.dump("xornet_deploy.mge", arg_names=["data"]) + pred_fun.dump("xornet_deploy.mge", arg_names=["data"], optimize_for_inference=True) 这里再解释一下编译与序列化相关的一些操作。编译会将被 :class:`~.trace` 装饰的函数(这里的 ``pred_fun`` )视为计算图的全部流程,计算图的输入严格等于 ``pred_fun`` 的位置参数(positional arguments,即参数列表中星号 ``*`` 前的部分,这里的 ``data`` 变量),计算图的输出严格等于函数的返回值(这里的 ``pred_normalized`` )。而这也会进一步影响到部署时模型的输入和输出,即如果运行部署后的该模型,会需要一个 ``data`` 格式的输入,返回一个 ``pred_normalized`` 格式的值。 -为了便于我们在 C++ 代码中给序列化之后的模型传入输入数据,我们需要给输入赋予一个名字,即代码中的 ``arg_names`` 参数。由于该示例中 ``pred_fun`` 只有一个位置参数,即计算图只有一个输入,所以传给 ``arg_names`` 的列表也只需一个字符串值即可,可以是任意名字,用于在 C++ 代码中引用,详情见下节内容。 +为了便于我们在 C++ 代码中给序列化之后的模型传入输入数据,我们需要给输入赋予一个名字,即代码中的 ``arg_names`` 参数。由于该示例中 ``pred_fun`` 只有一个位置参数,即计算图只有一个输入,所以传给 ``arg_names`` 的列表也只需一个字符串值即可,可以是任意名字,用于在 C++ 代码中引用,详情见下节内容。另外传递 ``optimize_for_inference=True`` (默认为 Flase)标志将在 ``dump()`` 方法中对模型针对 inference 进行优化,提高 inference 时候的模型运行效率。 总结一下,我们对在静态图模式下训练得到的模型,可以使用 :meth:`~.trace.dump` 方法直接序列化,而无需对模型代码做出任何修改,这就是“训练推理一体化”的由来。 @@ -48,7 +48,7 @@ MegEngine 的一大核心优势是“训练推理一体化”,其中“训练 接下来我们需要编写一个 C++ 程序,来实现我们期望在部署平台上完成的功能。在这里我们基于上面导出的异或网络模型,实现一个最简单的功能,即给定两个浮点数,输出对其做异或操作,结果为 0 的概率以及为 1 的概率。 -在此之前,为了能够正常使用 MegEngine 底层 C++ 接口,需要先按照 :ref:`installation` 从源码编译安装 MegEngine,并执行 ``make install`` 保证 MegEngine 相关 C++ 文件被正确安装。 +在此之前,为了能够正常使用 MegEngine 底层 C++ 接口,需要先按照 MegeEngine 中提供的编译脚本( `MegEngine/scripts `_ )从源码编译得到 MegEngine 的相关库, 通过这些脚本可以交叉编译安卓(ARMv7,ARMv8,ARMv8.2)版本、linux 版本(ARMv7,ARMv8,ARMv8.2)以及 ios 相关库,也可以本机编译 windows/linux/macos 相关库文件。 实现上述异或计算的示例 C++ 代码如下(引自 `xor-deploy.cpp `_ ): @@ -56,6 +56,7 @@ MegEngine 的一大核心优势是“训练推理一体化”,其中“训练 :language: cpp 简单解释一下代码的意思,我们首先通过 :ref:`exhale_class_classmgb_1_1serialization_1_1GraphLoader` 将模型加载进来,接着通过 ``tensor_map`` 和上节指定的输入名称 ``data`` ,找到模型的输入指针,再将运行时提供的输入 ``x`` 和 ``y`` 赋值给输入指针,然后我们使用 ``network.graph->compile`` 将模型编译成一个函数接口,并调用执行,最后将得到的结果 ``predict`` 进行输出,该输出的两个值即为异或结果为 0 的概率以及为 1 的概率 。 +另外可以配置上面加载模型时候的 ``config`` 来优化 inference 计算效率,为了加速一般在 ARM 上面配置 ``enable_nchw44_layout()`` ,在x86 CPU上面配置 ``enable_nchw88_layout()`` ,具体的配置方法参考 `load_and_run 源码 `_ 。 编译并执行 ------------------------------ @@ -64,9 +65,9 @@ MegEngine 的一大核心优势是“训练推理一体化”,其中“训练 .. note:: - 目前发布的版本我们开放了对 CPU(X86、X64)和 GPU(CUDA)平台的支持,后续会继续开放对 ARM 平台的支持。 + 目前发布的版本我们开放了对 CPU(X86、X64、ARMv7、ARMv8、ARMv8.2)和 GPU(CUDA)平台的 float 和量化 int8 的支持。 -我们在这里以 CPU 平台为例,直接使用 gcc 或者 clang (用 ``$CXX`` 指代)进行编译即可: +我们在这里以 CPU(X86) 平台为例,如果目标平台是ARM则可以参考 :ref:`inference_chinese` 。首先直接使用 gcc 或者 clang (用 ``$CXX`` 指代)进行编译即可: .. code-block:: bash @@ -84,4 +85,4 @@ MegEngine 的一大核心优势是“训练推理一体化”,其中“训练 Predicted: 0.999988 1.2095e-05 -至此我们便完成了从 Python 模型到 C++ 可执行文件的部署流程。 +至此我们便完成了从 Python 模型到 C++ 可执行文件的部署流程,如果需要快速的运行模型以及测试模型性能,请参考 :ref:`how_to_use_load_and_run` 。 -- GitLab