传统机器学习模型如何做在线预测

摘要

虽然目前深度学习的热度远远高过传统的机器学习,但仍然有很多实际问题更适合用传统机器学习模型解决。如何将这些机器学习模型发布到生产环境做在线预测仍是一个很有意义的问题。常见的机器学习模型包括但不限于:

  • 线性回归,Logistic 回归
  • 决策树
  • 随机森林
  • SVM
  • Boosting(AdaBoost,XGBoost)
  • 隐式马尔可夫

本文我们用一个实际的例子介绍如何使用 ONNX 生态的解决方案将 scikit-learn 与 hmmlearn 训练的机器学习模型发布为高性能的在线预测服务。我们将逐步解决如下问题:

  1. 如何将 scikit-learn 训练的模型转换为 ONNX 模型
  2. 如何在 C++ 编写的服务中使用 ONNXRuntime 做模型预测
  3. 如何支持自定义模型的转换和预测

文中所引用的实际可运行的代码均在 onnx-ml-demo 代码仓库下,读者可将其 git clone 到本地以方便查阅。

在开始运行该仓库的代码前,请运行 pip install -r requirements.txt 安装必要的依赖。

背景

好车主互助 APP 有一个 “危险驾驶行为 AI 智能识别系统”。用户打开该功能后,APP 就会开始采集手机的 GPS 定位,陀螺仪,加速度计的读数等信息,并将这些数据上传到云端,运行在云端的危险行为识别服务会根据这些数据判断用户开车时做了哪些危险动作。撰写此文时,好车主互助可以识别急加速,急刹车,急转弯,超速等多种危险行为,目前我们也在开发新的算法来识别更多种类的危险驾驶行为,例如夜间行车,疲劳驾驶,开车时玩手机等行为。

好车主互助 APP “危险驾驶行为 AI 智能识别系统” 功能截屏。左侧为行程采集界面,在该界面下 APP 会持续收集手机的传感器数据;右侧为滑动结束行程后的危险行为展示界面,图中展示的所有危险行为均由危险行为识别服务判定得出。

危险行为识别服务是一个用 C++ 编写的 gRPC 服务,里面实现了各种用于识别危险驾驶行为的算法,例如异常点过滤,滤波,平滑等。正在开发的开车玩手机行为识别采用了基于随机森林的分类和基于 HMM 的序列预测算法。在算法研发阶段我们用 scikit-learn 和 hmmlearn 完成了危险行为识别检测算法的调研和开发,算法的大致运行流程如下图所示:

算法接受的输入是一个 N x 3 的 tensor,其中 N 为 APP 采集的传感器数据的个数,每个传感器数据包含 3 个算法关心的属性,例如加速度计的读数,陀螺仪的读数等。

  1. 使用 StandardScaler 对输入样本做标准化,使每一个样本 x[i, :] 的值都在 [0, 1] 区间内
  2. 用随机森林做 0-1 分类,得到 N 个 0-1 分类的类别 ID 以及类别的 probability
  3. 对 2 中得到的 propability 做离散化映射到 6 个整数(0 - 5),得到长度为 N 的整数序列
  4. 将 3 中得到的整数序列做 HMM 推断,得到 N 个 0 - 1 之间的整数,该步骤得到的就是对输入序列的标注:如果某个样本的最终推断值为 1,则认为用户在该样本对应的时间点在玩手机。

整个算法的训练和预测过程实现在 train/train.py 和 train/infer.py。我们事先准备了一些合成的训练数据 data/synthetic.pkl 来演示整个流程。

现在我们要把这个算法集成到危险行为识别服务中,可能的实现路径有:

  1. 把整个算法用 C++ 重新实现一遍
  2. 用 FastAPI/Flask/Tornado/etc. 将识别算法包装成一个子服务供危险行为识别服务调用
  3. 利用第三方 C++ 算法库实现 scikit-learn 和 hmmlearn 模型的预测

其中路径1工作量较大,将来如果要用新的机器学习算法替换旧算法(例如用 AdaBoost 替换 RandomForestClassifier)需要重新开发;路径2需要运维一个额外的 Python 服务,并且 RPC 的可用性和延迟都不可控,危险识别服务还需要考虑子服务不可用时的容错问题,这又引入了额外的复杂度。

路径3有多种实现方案,我们调研了 sklearn-portercPMMLONNX 等多种方案。考虑到 ONNX 从成熟度,性能和可扩展性上都是比较好的选择,同时该方案可以兼容将来模型升级为基于深度学习的模型的情况,因此我们最终采用了基于 ONNX 的方案。

方法

什么是 ONNX

ONNX (Open Neural Network Exchange) 是一种用来表示深度学习模型的开放格式,自 2017 年推出以来逐渐被大多数主流机器学习框架支持。后来 ONNX 也在其规范中补充了对机器学习模型的支持 ONNX-ML,常用的机器学习包 scikit-learn 训练的大部分模型都可以通过 sklearn-onnx 转换为 ONNX 模型。ONNX 在其可交换的模型格式的基础上发展了一系列模型预测解决方案,可支持在 Intel/ARM CPU,CUDA 以及 Bitmain,OpenVINO 等边缘计算设备上使用 ONNX 模型运行深度学习预测。ONNXRuntime 就是其中一个支持多种平台的预测库,我们选用 ONNXRuntime 实现 x86_64 linux 服务器上的机器学习模型预测。

ONNX 模型

ONNX 模型就是一个计算图 (computation graph) 的描述。其实际的内部表示是一个 protobuf message,而 ONNX 模型文件就是将这个 protobuf message 序列化后直接存成的二进制文件。ONNX 的规范中包含了基本数据类型的定义,计算图的定义以及一些内建的算子的定义。开发自定义模型的 ONNX 转换器时可能需要查阅这部分规范。后面我们会简要介绍计算图的结构,以及如何查看 ONNX 模型的计算图。

训练模型

我们在代码库中附带了一组 Python 实现的模型训练和预测的代码,该代码中的预测流程和训练出的模型是我们今后讨论的基础。关于如何运行训练和预测脚本请参考 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值