ARTICLE DETAIL

资讯详情

深耕网站视觉设计与运营推广的一线实战洞察。

AI工程从零开始:从数据处理到模型部署的完整实践指南

AI工程从零开始:从数据处理到模型部署的完整实践指南 这几年总有人私信问我说想转行做AI一上来就问“我该学PyTorch还是TensorFlow”。我理解大家的焦虑但更想说清楚一件事如果你的目标写的是“ai-engineering-from-scratch”那模型框架只是路径上很小的一段。AI工程是“工程”不是“算法”。我做了几年AI落地相关的项目从小脚本到现在负责端到端链路踩过不少坑今天把从零开始的完整思路、方法、工具链和避坑经验整理出来。这篇文章更适合两类人一类是从算法/数据分析方向想往工程化走的朋友另一类是完全零基础、准备入行但不知道该从哪下手的初学者。我会尽量说人话把每个步骤背后的为什么都拆开。1. AI工程到底是什么先把这个概念框清楚1.1 算法、机器学习、AI工程的分界我见过不少人在简历上写“熟悉机器学习”结果连一个模型都没上过线。这不是讽刺而是很多初学者把“训练出一个高准确率模型”当成了终点。实际上训练模型只是AI工程这条流水线里的一个环节。算法同学解决的是“给定数据怎么优化目标函数”AI工程解决的是“怎么让模型稳定、高效、可维护地跑在真实业务里”。区别很大前者可以在Notebook里反复跑后者要面对的是数据漂移、版本兼容、资源调度、接口延迟、监控告警。我习惯用一个生活化的类比算法像是研发一道新菜你可以在家里厨房反复试盐多放少放都没关系AI工程是把这道菜做成中央厨房的标准化供应要考虑食材采购、切配标准、烹饪时间、冷链配送、用户投诉处理。很多刚入行的朋友只盯着“菜谱”忽略了“中央厨房”才是你能拿到高薪的核心。所以“from scratch”不是让你从线性回归推导开始而是让你从头搭建一套能把模型真正用起来的能力闭环。数据、训练、评估、部署、监控、迭代缺一环都不叫AI工程。1.2 一个AI项目的完整生命周期如果我在公司里接到一个新的AI需求脑子里会自动浮现一条流水线业务问题定义、数据采集与清洗、特征工程、模型训练与调优、离线评估、模型部署、在线监控、线上反馈回收。其中业务问题定义最容易被新人跳过。比如业务方说“我们要做一个推荐”你如果直接开始写模型大概率会失败。你要先弄清楚推荐什么、给谁推荐、在什么页面上、用户行为数据从哪里来、糟糕体验的定义是什么。AI工程的第一条军规就是“先确认问题再谈技术”。从数据到模型的环节大家相对熟悉但部署和监控往往被忽略。我记得第一次部署模型时以为只要把模型文件放到服务器上就结束了结果第二天准确率断崖式下跌。原因很简单线上特征分布变了模型没有自动感知能力而监控面板上根本没埋这个指标。后来的经验告诉我模型上线不是终点而是开始。线上推理日志、特征分布告警、定期重训任务这些才是工程化的重头戏。1.3 我建议的学习顺序不做课本的奴隶现在市面上的课程和书籍很多但大部分是“算法先导”的路径先学数学、再学模型、最后才提工程。对于“from scratch”的AI工程路径我建议反过来先建立端到端的整体感知再去补细节知识。先拿一个公开数据集跑通一个最简单的回归或分类任务然后把这个模型用FastAPI包成接口再用Docker把它容器化接着学一点监控比如记录推理耗时和预测分布。这个过程可能只需要一两周但它会在你的脑子里种下一个完整的“工程地图”。之后再去补数学、补分布式训练、补更深的模型原理你才知道每个知识点到底用在哪里。学习顺序不一定非要从泰勒公式开始。我在下面放了一张非常适合零基础入门的选型对照表都是开源且社区活跃的东西学起来不容易被带偏。环节推荐工具学习重点编程语言Python语法、面向对象、异常处理、装饰器数据处理pandas、NumPy、SQL数据清洗、聚合、关联查询模型训练scikit-learn、PyTorch训练循环、验证集、超参数实验管理MLflow记录参数、指标、模型产物接口封装FastAPIAPI设计、请求校验、异步处理容器化Docker镜像构建、依赖固化监控Prometheus、Grafana指标采集、可视化、告警调度编排GitHub Actions / Airflow自动化训练、定时重跑2. 地基先解决语言、数据和工具链2.1 Python不是万能的但它确实是AI世界的主语很多零基础的朋友问我是不是必须把Python学得很深才能开始。我的建议是不需要等你成为Python专家但至少要熟练到“不查语法也能写出一个类”的程度。AI工程的日常不是天天写模型而是写各种胶水代码从数据库读数据、清洗格式、调接口、拼参数、写定时任务。这些活儿考验的是基本功不是模型理解。我见过有同学一上来啃《流畅的Python》啃了两周就放弃了。其实可以先掌握列表推导、字典操作、函数、类、装饰器、with语句、try-except这些基础足够你写出干净可维护的代码。装饰器在FastAPI里会用到生成器在处理大文本时很有用这些边做边补更高效。Python相关的一个重要能力是“读错误日志”。新手经常跑了一行代码报错就慌。其实Python的错误信息已经把文件、行号、错误类型写得清清楚楚。要学会先读最后一行再往上找原因。这个习惯会伴随你整个AI工程生涯。2.2 数据处理能力比模型重要十倍很多人在训练时遇到“准确率上不去”第一反应是换模型。但实际上问题大概率出在数据上。AI工程中最耗时间的不是训练而是数据处理。一个真实的项目里你可能有70%的时间在干“数据苦力活”。我常用的组合是pandas SQL。SQL用来从公司数仓里捞数据pandas用来做探索性分析和清洗。新手可以先学会pandas的这几个操作读CSV、查看缺失值、fillna/dropna、groupby聚合、merge合并、apply自定义函数。这些操作覆盖了日常80%的需求。数据质量检查有一个容易被忽视的重点检查训练集和线上特征的一致性。比如训练时你用了“用户最近7天购买次数”线上如果拿到的特征延迟了一天这个偏差会直接导致模型效果变差。这不是模型能自己纠正的。我的习惯是把特征定义写成一个单独的函数训练和推理共用同一份代码从根源上避免两端特征不一致。2.3 环境管理从依赖地狱到可复现AI工程的“脏活”之一就是管理依赖。今天装个torch明天装个sklearn后天升级了numpy结果另一个项目跑不起来了。我最早也遇到过这种问题一天时间都耗在配环境上。我现在的标配是conda Docker两件套。本地开发用conda创建隔离环境每个项目一个环境Python版本和依赖都写进environment.yml。到了要部署的环节用Docker把代码、依赖、系统库全部打包成镜像这样不管部署到哪个服务器跑起来的效果都和本地一致。新手经常忽略锁版本。pip的requirements.txt如果写成“numpy1.19”这个“”会带来极大的不确定性。今天跑通三个月后可能就装上了不兼容的版本。建议把依赖固化成具体版本号比如numpy1.21.4。更进一步可以使用pip-tools或poetry生成锁定版本的lock文件。环境可复现是所有工程化的基础。3. 模型开发从训练到评估的工程化习惯3.1 训练脚本的规范化别再把所有代码塞进NotebookNotebook适合做探索但不适合做工程。我在带项目时要求所有训练代码必须转成脚本并且要有清晰的目录结构。一个最基本的训练项目目录大概是这样的project/ ├── data/ # 原始数据和中间数据 ├── src/ │ ├── data_process.py # 数据清洗、特征工程 │ ├── train.py # 训练入口 │ ├── evaluate.py # 离线评估 │ └── predict.py # 推理封装 ├── models/ # 模型产物 ├── config.yaml # 参数配置 └── requirements.txt # 依赖清单目录结构本身不是目的目的是让任何人拿到你的仓库都能跑起来。训练脚本要有参数入口比如通过argparse读取--batch_size、--lr、--epochs。不要把这些值硬编码在文件里。配置文件和代码分离这个习惯能帮你后面做自动化训练。训练过程还要保存有效的Checkpoint。不能只在训练结束后保存最终模型最好每个epoch或每个best模型都存一份。存的时候带上训练参数、数据版本、评估指标。因为当你后来发现指标异常时需要能回滚到之前的版本排查问题。3.2 实验管理不要用Excel记录训练结果早期我自己也是用Excel记实验记了几次就放弃了。实验多了以后你根本记不住哪组超参对应哪个模型。更麻烦的是模型文件名和实际参数对不上回查时欲哭无泪。后来我换成了MLflow这是目前开源社区里最常用的实验管理工具之一。MLflow可以自动记录每个实验的参数、指标、模型产物并提供一个Web界面按时间排序。你训练时只需要在代码里加几行import mlflow with mlflow.start_run(): mlflow.log_param(lr, 0.001) mlflow.log_param(batch_size, 32) mlflow.log_metric(auc, 0.86) mlflow.pytorch.log_model(model, model)这样做的好处是任何一次实验的完整上下文都在。你只要打开MLflow UI就能对比不同实验的指标、参数还能直接加载某个run的模型做测试。对于团队协作来说实验记录统一化也避免了“你用的是哪版模型”这种低水平沟通。3.3 评估指标别只盯着准确率我在面试的时候经常问一个问题如果正负样本是99比1你的模型准确率99%这模型有价值吗答案是基本没价值因为全部预测成负样本也能达到99%。这个例子在AI工程里非常实际。分类问题要关注Precision、Recall、F1回归问题要关注MAE、RMSE排序问题要看NDCG、AUC。更重要的是指标一定要贴合业务目标。比如做欺诈检测漏掉一笔欺诈交易的成本很高所以召回率要优先做商品推荐用户不想看到太多不相关的东西精度可能更重要。工程实现上评估代码必须和训练代码分离保证测试集不泄露到训练过程中。最稳妥的做法是单独写一个evaluate.py从数据目录读取留出的验证集对模型产物做评估。4. 上线部署让模型开始真正干活4.1 模型服务化用FastAPI封装一个推理接口模型训练完成后下一个问题是怎么让业务系统调用它。最朴素的办法是写一个Python脚本加载模型后对输入数据做预测但这种方式太笨重。我一般用FastAPI把模型包成一个HTTP服务一次加载模型常驻内存接收请求后返回预测结果。一个最小可用的服务大概长这样from fastapi import FastAPI from pydantic import BaseModel import joblib app FastAPI() model joblib.load(models/model.joblib) class InputData(BaseModel): feature1: float feature2: float app.post(/predict) def predict(data: InputData): x [[data.feature1, data.feature2]] pred model.predict(x)[0] return {prediction: float(pred)}这里有几个工程细节容易踩坑。第一模型加载要在模块导入时完成不能每个请求都重新加载否则延迟高到没法用。第二输入参数要有类型校验Pydantic在这里帮了大忙传错类型直接返回400。第三批量推理比单条推理吞吐量高很多如果业务方有一批数据要打分可以设计一个/batch_predict接口接收数组输入。上线前还要考虑超时和异常处理。如果模型内部抛了异常不能让用户看到堆栈要捕获异常后返回统一的错误码并记录日志。这些细节决定了你这个接口是“演示级”还是“生产级”。4.2 容器化部署Docker不是可选项如果只在自己电脑上跑模型不学Docker也没问题。但一旦需要部署到公司服务器或云环境Docker就是迈不过去的门槛。它解决的核心问题是环境一致性本地装好的依赖、系统库、Python版本全部打包进镜像服务器上直接跑不需要手动配环境。一个简单的Dockerfile长这样FROM python:3.9-slim WORKDIR /app COPY requirements.txt . RUN pip install --no-cache-dir -r requirements.txt COPY ./app /app CMD [uvicorn, main:app, --host, 0.0.0.0, --port, 8000]新手有几个常见问题。第一镜像基础不要选“latest”要明确版本否则某天基础镜像更新后你的服务可能就起不来了。第二COPY代码之后要记得把不需要的文件写进.dockerignore比如本地数据集、模型文件避免镜像过于臃肿。第三容器内的进程要和容器的生命周期绑定否则容器启动后进程pid为1的不是你的服务会出现容器还在但服务已经挂掉的情况。镜像构建好之后可以用docker run本地验证一遍再推送到镜像仓库后续的部署、滚动更新都基于这个镜像进行。只要能保证镜像可复现上线就不再是玄学。4.3 监控与反馈模型上线不是终点很多模型的失效都不是突然崩溃而是缓慢退化。数据分布变了、用户习惯变了、上游特征质量变了都会让模型指标一点点下滑。如果没有监控业务方可能比你先发现问题那时候就相当被动了。监控要做两层。第一层是系统监控重点关注接口延迟、吞吐量、错误率、内存和CPU使用率。推荐用Prometheus采集指标用Grafana画看板。第二层是模型监控需要统计线上预测结果的分布比如分类问题里“预测为正样本的比例”是不是突然升高了。如果分布发生明显偏移就要考虑重新训练或回滚版本。我这里做了一个简单的问题排查表不一定全面但都是日常最常见的隐患。现象可能原因排查思路线上准确率下降特征分布漂移比较训练和线上的特征均值/分布接口响应变慢推理数据量过大或CPU瓶颈查看监控指标考虑批量推理偶发报错输入数据缺失或类型异常检查Pydantic校验和异常日志模型效果一直上不去训练数据泄漏检查时间序列划分是否严格5. 常见问题与排查实录5.1 数据泄漏静悄悄地拉高你的指标数据泄漏是AI工程里最“阴险”的问题之一。现象是离线评估指标特别漂亮一上线就垮。我踩过一个真实的坑做某个时序预测任务时因为清洗逻辑写错了把未来信息混进了训练特征。离线的AUC高达0.97线上实际效果排名却垫底。排查数据泄漏有两点经验可以分享。第一在特征工程阶段任何聚合操作都要反复检查时间窗口比如“用户历史购买统计”只能用当前时间点之前的记录不能让预测时刻之后的数据参与计算。第二在数据划分上不要随便用train_test_split处理时间序列数据要用时间序列切分保证训练集完全在验证集之前。泄漏带来的“高指标”是幻觉工程上宁可要一个真实的、稍微低一点的指标。5.2 训练复现困难随机种子和版本锁同一个模型脚本第一次跑AUC是0.85第二次跑变成0.84这是很多新人的困惑。原因通常是随机性随机初始化、随机数据Shuffle、GPU的非确定性运算。要保证训练可复现第一步是在代码里固定随机种子import random import numpy as np import torch def set_seed(seed): random.seed(seed) np.random.seed(seed) torch.manual_seed(seed)但这还不够深度学习框架的某些操作比如某些CUDA并行计算即使固定种子也可能有微小偏差。如果实验要求完全可复现需要设置torch.backends.cudnn.deterministic True同时关闭benchmark模式。更实用的是记录“数据版本代码版本依赖版本参数配置”一旦结果异常可以回到当时的实验环境。5.3 内存和显存管理OOM不是玄学跑模型时最常见的报错是OutOfMemoryCPU内存不够和GPU显存不够的表现不一样。CPU内存不够通常是因为一份数据被复制了很多份。比如pandas读了一个大文件你做了过滤又做了merge原始DataFrame还占着内存。建议及时del掉不用的中间变量或者用gc.collect()手动回收。GPU显存不够原因可能是batch_size太大、输入图片过大或者模型本身太大。这时候优先调小batch_size观察显存占用变化。如果有多个模型同时加载可以考虑用CPU跑部分模型或者用推理服务框架做模型分片。不要一遇到OOM就崩心态先看显存是持续涨还是一下子爆这能帮你判断是内存泄漏还是批次过大。5.4 延迟和吞吐优化别等到上线再想有些模型在离线评估时算得挺快一上线发现接口平均延迟1秒根本扛不住。原因可能是单条推理循环、未做批量处理、特征计算逻辑过于复杂。我一般会分三步优化先做特征计算耗时分析找出瓶颈然后看模型推理部分能否用torch.jit或ONNX加速最后考虑在服务层面加缓存高频且重复的请求直接从Redis里取结果。这里有一个性价比很高的做法把不需要实时推理的场景全部转成离线批量预测。比如“每日用户评分”完全可以用定时任务每天凌晨算好结果写到数据库里白天直接查表。实时推理的复杂度高、成本大工程上能做离线就尽量离线。6. 一条可复制的从零到一实操路径6.1 用十周时间完成一个小而全的AI项目如果你看完上面这些内容还是不知道怎么动手我建议你直接给自己定一个十周的小项目。选一个经典又简单的场景比如“客户流失预测”或者“电影评分预测”。第一周搭好Python环境和项目目录第二周用pandas做数据探索和清洗第三周用scikit-learn训练一个逻辑回归模型当基线第四周用MLflow记录所有实验第五周用FastAPI包一个推理接口第六周把服务装进Docker第七周加一点监控指标第八周做一次参数调优第九周整理文档第十周复盘整个链路。这个过程里的每一步都会逼你用到真实工程中的技能。做完之后你会对“ai-engineering-from-scratch”这句话有非常具体的理解。它不是一个名词而是一条从数据到价值的完整生产线。很多知识点一开始看不明白是因为没有上下文等你亲手跑完一个全流程再看论文和源码理解深度完全不一样。6.2 最后分享一点我的个人体会做AI工程这几年我最大的感受是会调模型的人很多能把模型稳定变成业务价值的很少。公司里缺的从来不是“会跑通一个Notebook”的人而是能扛住数据质量、模型上线、监控告警、故障恢复这一系列脏活的人。从零开始不是让你把论文公式背一遍而是让你亲手把每个环节都做一遍踩一遍坑然后理解为什么工程化要这么设计。如果你已经在路上别怕慢多试错、多复盘这条路是真实可以走通的。
返回列表