AI Pro 部署 yolov8 目标检测模型 -- 导出int8量化模型(1)
yolov8 是一个单阶段的CV模型,包含目标检测,也可以用于分类、分割和关键点预测(https://github.com/ultralytics/ultralytics)。作为项目部署是个不错的选择,试试部署+运行在边缘设备香橙派AIpro。yolov8-nano 模型速度为 102fps,resnet50 速度为280fps。看看表现吧。

前置工作
使用笔记本电脑,ssh远程连接到AI pro。
- 「AI pro」使用镜像 opiaipro_ubuntu22.04_desktop_aarch64_20240202.img.xz 。
- 「AI pro」使用 root 账号登陆。因为NPU的调度需要 root 权限,即使 sudo 都不好使。
- (推荐)「AI pro」开启 mindx sdk,执行命令 source /usr/local/Ascend/mxVision/set_env.sh
- 「AI pro 或 笔记本」安装 amct_onnx 昇腾模型量化工具,不量化就忽略该操作。
- 「AI pro 或 笔记本」 pip install onnx onnxruntime 等工具包。在安装 amct_onnx 时,已经自动安装了。
- 「笔记本」下载和安装 ultralytics-yolo 的开发环境。
由于 AI pro 上已经配置了 CANN + MINDX 环境,再装一个 amct 就容易凑齐全家桶了。从零开始配置笔记本的 CANN + MINDX + acmt 太费劲。
工作流程
非量化模型,fp16
pytorch -> onnx -> om
量化模型,int8, 算力翻倍
pytorch -> onnx -> onnx_deploy (int8) -> om
1. 下载或训练自己的yolo模型 [笔记本电脑]
这里我选用的是官方 yolov8-det-nano 模型。你也可以选择 seg、cls,或者将自己训练的模型导出为 ONNX 文件。
得到 yolov8n.onnx, 将其从笔记本中拷贝到 香橙派 AI pro。剩下的操作都在 AI pro 中进行。
2. (可选,推荐)检查 ONNX 的输入输出维度,可以修改 batchsize
模型量化和导出,都需要知道 ONNX 模型的输入节点的维度以及名称,不能有误。可以使用作者的工具 onnx_inspect 检查。
记录输入节点的名称 images,维度 (1, 3, 640, 640)。
模型的batchsize 是1,可以将其修改为其它size,或者是 dynamic batchsize 。尤其在模型的量化中,使用dynamic batchsize更好的兼容多张图片的 Evaluation。
通过本人提供的 onnx_rebatch 工具,将 yolov8n.onnx 修改为动态batchsize 的 yolov8n_batchdynamic.onnx。修改后,输入节点的名称依然为 images,维度 (N, 3, 640, 640)
不量化,直接转 OM
这样最简单,输出的是 float16 计算精度的模型,计算速度折中。
3. 量化模型
首先,要将data/images目录下的jpg文件处理为data/calibration目录下的bin文件。
参考 python/level1_single_api/9_amct/amct_onnx/cmd · Ascend/samples - 码云 - 开源中国 (gitee.com) 里面的步骤、数据和代码。下载对应的数据集。拷贝和修改samples/python/level1_single_api/9_amct/amct_onnx/cmd/src/process_data.py 。
具体注意事项:
- YOLO 的输入维度 (N, 3, h=640, w=640), 所以设定图片resize也为 (640, 640).
- CALIBRATION_SIZE 是用来量化的图片总数,数量越多量化的效果越好。但它需要和onnx 的batchsize 保持一致。如果使用 yolov8n.onnx, 则必须使用 CALIBRATION_SIZE =1 。使用 yolov8n_batchdynamic.onnx 时,可以设置更大的CALIBRATION_SIZE。
- YOLO 图片的像素数值归一化是 uint8 / 255.0,不需要设定 MEAN 和 STD。
执行图片预处理
- 将得到 data/calibration/calibration.bin ,是用于模型压缩的数据集,包含CALIBRATION_SIZE 张图片。
执行ONNX模型压缩(int8 量化):
- 将得到量化后的 ONNX 文件, yolov8n_deploy_model.onnx。由于是int8压缩,文件体积更小。
amct_onnx calibration --model model/yolov8n_batchdynamic.onnx --input_shape "images:16,3,640,640" --data_type "float32" --data_dir ./data/calibration/ --save_path ./results/yolov8n
4. 压缩的ONNX 再转 OM
用 atc 工具,正常转换就可以。
5. 性能测试
- 不包含 图片的pre-processing, 也不包含数据的post-processing。
单独开一个终端,用于检测 NPU 的使用率

检查 'mind sdk' 是否安装和配置:
- 看到下面的输出,表明 mind sdk 的配置是成功的
可以看到 YOLOV8n 经过模型量化(int8)之后,在AI pro上的速度为 102 fps。相较于 CPU 上的模型提升 50x,NPU 的确更适合模型推理。模型量化前后,没有提升,可能存在瓶颈。
YOLOV8n 没法吃满 NPU 的算力,即使多线程也只能使用NPU一半的性能。这应该是 CPU float32(1, 3, 640, 640) ==> NPU 数据传输太慢的问题。在跑 resnet50.om 量化模型的时候,输入尺寸(1,3,224,224), NPU 能够占用NPU 88%,fps 达200,说明NPU本身没有问题。而 AI pro 的CPU和内存都比较慢,大体积的数组拷贝非常吃力。
即使 numpy 数组在内存中克隆, AI pro速度也是非常慢的,是香橙派5(rk3588, 8G内存)的约 1/4 速度。详细数据未展示。
Resnet 模型推断速度
resnet (224x224) 推理速度
模型量化前后,速度有提升。接近理论的2倍提升。
6. 总结
这套模型量化,可以适用 yolo 系列,也可以用于 resnet 等其它网络。受限于内存的瓶颈,int8 量化对于 yolo 轻量模型没有增益。对于计算密集的模型,量化才有显著的提升作用。
AI Pro 部署 yolov8 目标检测模型 -- 导出int8量化模型(1)
yolov8 是一个单阶段的CV模型,包含目标检测,也可以用于分类、分割和关键点预测(https://github.com/ultralytics/ultralytics)。作为项目部署是个不错的选择,试试部署+运行在边缘设备香橙派AIpro。yolov8-nano 模型速度为 102fps,resnet50 速度为280fps。看看表现吧。
前置工作
使用笔记本电脑,ssh远程连接到AI pro。
由于 AI pro 上已经配置了 CANN + MINDX 环境,再装一个 amct 就容易凑齐全家桶了。从零开始配置笔记本的 CANN + MINDX + acmt 太费劲。
工作流程
非量化模型,fp16
pytorch -> onnx -> om
ultralytics
atc
量化模型,int8, 算力翻倍
pytorch -> onnx -> onnx_deploy (int8) -> om
yolov8n_deploy_model.onnx
ultralytics
amct_onnx
atc
1. 下载或训练自己的yolo模型 [笔记本电脑]
这里我选用的是官方 yolov8-det-nano 模型。你也可以选择 seg、cls,或者将自己训练的模型导出为 ONNX 文件。
# 官方模型 yolov8n.pt python -c "from ultralytics import YOLO;YOLO('yolov8n').export(format='onnx')" # 自己模型 python -c "from ultralytics import YOLO;YOLO('PATH_TO_MY_YOLO.pt').export(format='onnx')" mv yolov8n.onnx model/得到 yolov8n.onnx, 将其从笔记本中拷贝到 香橙派 AI pro。剩下的操作都在 AI pro 中进行。
2. (可选,推荐)检查 ONNX 的输入输出维度,可以修改 batchsize
模型量化和导出,都需要知道 ONNX 模型的输入节点的维度以及名称,不能有误。可以使用作者的工具 onnx_inspect 检查。
root@orangepiaipro# onnx_inspect model/yolov8n.onnx [I] Loading model: model/yolov8n.onnx [I] ==== ONNX Model ==== Name: torch-jit-export | ONNX Opset: 14 ---- 1 Graph Input(s) ---- images [dtype=float32, shape=(1, 3, 640, 640)] ---- 1 Graph Output(s) ---- output0 [dtype=float32, shape=('Concatoutput0_dim_0', 'Concatoutput0_dim_1', 'Concatoutput0_dim_2')] ---- 138 Initializer(s) ---- ---- 286 Node(s) ----记录输入节点的名称 images,维度 (1, 3, 640, 640)。
模型的batchsize 是1,可以将其修改为其它size,或者是 dynamic batchsize 。尤其在模型的量化中,使用dynamic batchsize更好的兼容多张图片的 Evaluation。
root@orangepiaipro# onnx_rebatch model/yolov8n.onnx --batch 0 # to dynamic root@orangepiaipro# onnx_inspect model/yolov8n_batchdynamic.onnx [I] Loading model: model/yolov8n_batchdynamic.onnx [I] ==== ONNX Model ==== Name: torch-jit-export | ONNX Opset: 14 ---- 1 Graph Input(s) ---- images [dtype=float32, shape=('N', 3, 640, 640)] ---- 1 Graph Output(s) ---- output0 [dtype=float32, shape=('N', 'Concatoutput0_dim_1', 'Concatoutput0_dim_2')] ---- 138 Initializer(s) ---- ---- 286 Node(s) ----通过本人提供的 onnx_rebatch 工具,将 yolov8n.onnx 修改为动态batchsize 的 yolov8n_batchdynamic.onnx。修改后,输入节点的名称依然为 images,维度 (N, 3, 640, 640)
不量化,直接转 OM
这样最简单,输出的是 float16 计算精度的模型,计算速度折中。
root@orangepiaipro# atc --model=model/yolov8n.onnx --framework=5 \ --output=model/yolov8n --input_shape="images:1,3,640,640" \ --soc_version=Ascend310B4 root@orangepiaipro# onnx_inspect model/yolov8n.om [I] Loading model: model/yolov8n.om [I] ==== OM Model ==== ---- 1 Graph Input(s) ---- #0 [dtype=float32, shape=(1, 3, 640, 640)] ---- 1 Graph Output(s) ---- #0 [dtype=float32, shape=(1, 84, 8400)]3. 量化模型
首先,要将data/images目录下的jpg文件处理为data/calibration目录下的bin文件。
参考 python/level1_single_api/9_amct/amct_onnx/cmd · Ascend/samples - 码云 - 开源中国 (gitee.com) 里面的步骤、数据和代码。下载对应的数据集。拷贝和修改samples/python/level1_single_api/9_amct/amct_onnx/cmd/src/process_data.py 。
具体注意事项:
# src/process_data.py ... WIDTH, HEIGHT = 640, 640 CALIBRATION_SIZE = 16 ... def prepare_image_input(images, height=HEIGHT, width=WIDTH): """Read image files to blobs [batch_size, 3, 224, 224]""" input_array = np.zeros((len(images), 3, height, width), np.float32) mean = MEAN std = STD imgs = np.zeros((len(images), 3, height, width), np.float32) for index, im_file in enumerate(images): im_data = cv2.imread(im_file) im_data = cv2.resize( im_data, (width, height), interpolation=cv2.INTER_CUBIC) cv2.cvtColor(im_data, cv2.COLOR_BGR2RGB) imgs[index] = im_data.transpose(2, 0, 1).astype(np.float32) input_array = imgs # trans uint8 image data to float input_array /= 255 return input_array ...执行图片预处理
执行ONNX模型压缩(int8 量化):
4. 压缩的ONNX 再转 OM
用 atc 工具,正常转换就可以。
root@orangepiaipro# atc --model=model/yolov8n_deploy_model.onnx --framework=5 \ --output=model/yolov8n_deploy_model --input_shape="images:1,3,640,640" \ --soc_version=Ascend310B4 root@orangepiaipro# onnx_inspect model/yolov8n_deploy_model.om [I] Loading model: model/yolov8n_deploy_model.om [I] ==== OM Model ==== ---- 1 Graph Input(s) ---- #0 [dtype=float32, shape=(1, 3, 640, 640)] ---- 1 Graph Output(s) ---- #0 [dtype=float32, shape=(1, 84, 8400)]6.8M
5. 性能测试
单独开一个终端,用于检测 NPU 的使用率
检查 'mind sdk' 是否安装和配置:
onnx_speed model/yolov8n.onnx
OM FP16
echo "1 2 3 4" | xargs -n 1 -P 0 onnx_speed model/yolov8n.om -i
OM INT8
可以看到 YOLOV8n 经过模型量化(int8)之后,在AI pro上的速度为 102 fps。相较于 CPU 上的模型提升 50x,NPU 的确更适合模型推理。模型量化前后,没有提升,可能存在瓶颈。
YOLOV8n 没法吃满 NPU 的算力,即使多线程也只能使用NPU一半的性能。这应该是 CPU float32(1, 3, 640, 640) ==> NPU 数据传输太慢的问题。在跑 resnet50.om 量化模型的时候,输入尺寸(1,3,224,224), NPU 能够占用NPU 88%,fps 达200,说明NPU本身没有问题。而 AI pro 的CPU和内存都比较慢,大体积的数组拷贝非常吃力。
Resnet 模型推断速度
resnet (224x224) 推理速度
Resnet50
INT8 量化
模型量化前后,速度有提升。接近理论的2倍提升。
6. 总结
这套模型量化,可以适用 yolo 系列,也可以用于 resnet 等其它网络。受限于内存的瓶颈,int8 量化对于 yolo 轻量模型没有增益。对于计算密集的模型,量化才有显著的提升作用。