Skip to content

ONNX Runtime 推理说明 ​

1. 为什么使用 ONNX Runtime ​

在训练阶段,目标检测模型通常使用 PyTorch / Ultralytics YOLOv8 完成。 但在生产环境(Java 服务端、Android 等)无法直接运行 Python 推理,因此需要:

将训练好的模型导出为 ONNX → 使用 ONNX Runtime 执行推理

ONNX Runtime 是微软维护的高性能跨平台推理引擎,特点:

  • 不依赖 Python
  • 内存占用低
  • 启动速度快
  • 多线程推理稳定
  • 支持 CPU / CUDA / TensorRT
  • 可部署服务端和移动端

因此 Java 项目中,深度学习推理的标准方案就是:

PyTorch 训练 → 导出 .onnx → Java 使用 ONNX Runtime 推理

2. YoloV8推理整体流程 ​

完整的检测流程如下:

图片字节
   ↓
OpenCV 解码
   ↓
预处理 (Resize + Letterbox + Normalize)
   ↓
构造 Tensor (OnnxTensor)
   ↓
ONNX Runtime 推理 (session.run)
   ↓
原始输出矩阵
   ↓
后处理 (Sigmoid + 阈值过滤 + NMS)
   ↓
映射回原图坐标
   ↓
DetectionResult

3. ONNX Runtime 核心组件 ​

3.1 OrtEnvironment —— 推理引擎环境 ​

java
OrtEnvironment env = OrtEnvironment.getEnvironment();

作用:

创建 ONNX Runtime 全局运行环境

理解方式: 类似 JVM 是 Java 程序的运行基础,OrtEnvironment 是 AI 推理的运行基础。

特点:

  • 全局唯一
  • 生命周期贯穿整个服务
  • 管理线程池、算子库、内存分配

3.2 OrtSession —— 已加载的模型 ​

java
OrtSession session = env.createSession(modelPath, sessionOptions);

作用:

将 .onnx 模型加载到内存并构建计算图

可以理解为:

磁盘模型 → 神经网络结构 → 可执行推理图

它等价于 Python 中:

python
model = YOLO("model.onnx")

注意:

  • Session 创建成本很高
  • 必须复用
  • 不允许每次请求重新加载模型

3.3 OnnxTensor —— 输入数据容器 ​

java
OnnxTensor tensor = OnnxTensor.createTensor(env, FloatBuffer.wrap(pixels), shape);

作用:

将 Java 数组转换为神经网络输入张量

深度学习模型不接收图片对象,而是接收 Tensor(多维浮点矩阵)

YOLOv8 输入格式:

[batch, channel, height, width] = [1, 3, 640, 640]

因此需要:

Mat → float[] → FloatBuffer → OnnxTensor

3.4 session.run() —— 执行推理 ​

java
OrtSession.Result outputs = session.run(inputs);

作用:

真正执行神经网络计算

过程:

CPU/GPU 执行卷积网络→ 输出候选框矩阵

返回的并不是最终检测框,而是 原始预测张量

YOLOv8 输出通常为:

[1, 84, 8400] 或 [1, 8400, 84]

含义:

位置含义
8400候选检测框数量
4x,y,w,h
1objectness
nc分类概率

4. 推理后的后处理 ​

ONNX Runtime 只负责神经网络计算,不负责目标检测逻辑。 YOLO 的真正结果需要自行解析。

后处理步骤:

4.1 转置输出 ​

模型输出是按通道排列,需要转为按候选框排列:

[C][N] → [N][C]

4.2 Sigmoid 处理 ​

部分 ONNX 导出模型输出的是 logits,需要:

score = sigmoid(score)

4.3 置信度过滤 ​

confidence > confThreshold

剔除低概率框,减少 NMS 计算量。


4.4 坐标转换 ​

YOLO 输出:

xywh (中心点 + 宽高)

需要转换为:

xyxy (左上角 + 右下角)

4.5 NMS 非极大值抑制 ​

目的:

去掉重复检测框

保留重叠度最低的一组目标。


4.6 映射回原图坐标 ​

由于推理使用了 letterbox:

640x640 模型坐标 → 原始图片坐标

需要反变换:

(x - padding) / scale

5. 生命周期管理 ​

初始化(应用启动) ​

创建 OrtEnvironment
加载 OrtSession
创建线程池

推理(每次请求) ​

构造 Tensor
session.run()
解析输出

关闭(服务退出) ​

session.close()
env.close()

6. 设计原则 ​

  1. 模型只加载一次
  2. Session 必须复用
  3. 推理必须并发控制
  4. Tensor 使用后必须释放
  5. 推理必须设置超时
  6. 后处理必须在 Java 侧完成

7. 一句话理解 ​

ONNX Runtime 的职责只有一个:执行神经网络计算。

组件职责
OrtEnvironmentAI 引擎运行环境
OrtSession已加载的模型
OnnxTensor输入数据
session.run()执行推理
后处理代码解析 YOLO 输出

这套结构本质上就是:

用 Java 实现一套不依赖 Python 的 YOLO 推理服务。

8. onnx常见错误 ​

MIT Licensed