资讯动态

YOLOv5垃圾分类检测系统实战:从数据标注到模型改进与部署

发布时间:2026/10/20 15:49:40 来源:尧图企业网站定制
第一次有人让我做垃圾分类识别是在半年前。一个做智能设备的开发者跑来问我能不能给他们的智能分类箱装一双眼睛把投入的垃圾自动认出来这样就不用靠人站在桶边指导。我当时第一反应是这有什么难的深度学习的YOLOv5垃圾识别检测系统不是满地都是文章吗。但真正动手以后才发现从能跑通一个开源Demo到真的敢在垃圾分类数据集上做训练、做算法改进、再做一套实时检测系统原型中间隔着一整套工程问题。这个项目我前后折腾了快两个月做完之后我把它定义为一个标准的分阶段AI项目实战第一阶段是垃圾分类数据集构建和清洗第二阶段是YOLOv5模型训练、验证和三类算法改进第三阶段是同数据集下的模型对比实验第四阶段是把权重部署成实时检测系统原型接摄像头、做界面、做推理优化。整套流程非常适合做毕业设计、课程设计、或者一个环保领域的算法验证项目。这篇文章我就把从数据到部署的全过程、包括踩过的坑和最终结论一次性讲透。1. 从识别垃圾到垃圾分类箱项目到底要解决什么问题1.1 需求的真实面貌很多人上来就以为垃圾识别就是一个单纯的目标检测Task输入图片输出 bounding box 和类别。但实际接触真实需求后你会发现用户真正想要的是一个分类决策结果。比如一个纸杯它到底是可回收物还是其他垃圾在某些城市的分类标准里答案都不一样一个沾了油的外卖盒外观看着是纸质但按很多地方的标准应该扔进其他垃圾。也就是说模型输出这是纸盒并不够系统还要结合垃圾分类规则决定它该进哪个桶。所以我在项目设计一开始就把问题拆成了两层底层是目标检测负责识别视觉物品种类上层是规则映射把物品种类映射到厨余垃圾、可回收垃圾、有害垃圾、其他垃圾这四类。这个分层的好处是检测模型只需要专注看得清、认得准分类规则则在代码里随时可配置今天按A标准执行明天换成B标准只改映射表就行不用重训模型。1.2 为什么最终选了YOLOv5这棵树在确定技术方案时我没有一上来就追最新的检测架构而是对比了几条路线老牌的Faster R-CNN、精度高的两阶段检测器、刚兴起的一批基于Transformer的检测模型以及YOLO系列。最后落到YOLOv5上不是因为它的精度在所有数据集上都最高而是因为它在这类项目里综合体验最好。部署友好YOLOv5的模型导出链路非常顺PyTorch训练完直接转ONNX再转其他推理引擎都方便做实时摄像头推理时帧率很好控制。迭代快、社区资料多遇到任何奇怪问题基本上搜一下都有答案做项目最怕的不是技术难而是卡在一个环境问题上三天出不来。改进空间明确YOLOv5的Backbone、Neck、Head结构清晰做算法改进实验、画消融对比表非常方便适合需要汇报我做了什么改进的场景。我用一句话总结这个选型逻辑在不需要冲击某个特定Benchmark榜首的前提下YOLOv5是从零搭一个能跑、能改、能部署的识别系统性价比最高的起点。2. 数据是第一个拦路虎垃圾分类数据集折腾全过程2.1 数据来源与类别体系设计模型效果的上限是被数据决定的这句话在垃圾分类项目里体现得特别明显。我最初尝试直接用网上公开的垃圾分类图片集类别倒是齐全但真实场景照片很少大多数是纯色背景的商品图。把这种数据训出来的模型拿到垃圾桶旁边一测光线一变、角度一变、旁边再有几个其他垃圾叠在一起检测框就开始乱跳。所以我最终的数据策略是公开底料自采补充针对性增强三管齐下。底料用公开来源里相对干净的图片自采则是在实际场景下补拍了一批覆盖不同光照、不同遮挡、不同摆放姿态。类别的设计上我没有直接按四分类桶来标注而是细分成具体物品比如塑料瓶、易拉罐、纸箱、玻璃瓶、塑料袋、水果皮、菜叶、废电池、过期药品、烟头等。这样做的原因前面说了检测模型负责物品识别分类规则由上层决定细分类别越多未来适配不同地区分类标准就越灵活。2.2 标注质量与类别不平衡的教训标注阶段我第一次体会到什么叫脏活累活。几千张图片、几万个框真的会标到怀疑人生。但我后来复盘这部分的教训主要是三个第一标注框的边界不一致会让模型学得很混乱。一个矿泉水瓶有人沿着瓶身标有人把瓶盖也算进去还有人连阴影带上了。这样的标签训练出来的回归头会犹豫表现在结果上就是检测框忽大忽小。我后来做了两轮交叉复查把所有明显露出背景过多和框切掉物体边缘的标注都修了一遍才正式开始训练。第二类别不平衡是隐蔽的精度杀手。易拉罐、塑料瓶这类常见垃圾样本量大模型自然认得准但纽扣电池、玻璃碎片这种出现频率低、样本又少的类别很容易被模型直接忽略。处理方式我后面单独讲这里先记住一个结论不要只看总体mAP要看每个类别的AP分布否则某个低频类别的识别率低到你不敢用。第三背景干扰比想象中严重。垃圾识别场景里物体经常是堆叠的、半遮挡的而且垃圾桶本身、地面纹理、手部都可能成为干扰。我一开始没有在数据里刻意加入这些困难样本后来发现模型把地面上的落叶当成其他垃圾的概率高得离谱才回头专门补了一批带干扰的负样本和困难样本。2.3 数据增强我用过的几种有效组合在数据增强策略上我并没有盲目堆叠所有手段。经过几轮A/B对比最后留下了一套比较稳的组合随机仿射变换包括旋转、平移、缩放模拟投放垃圾时各种非正立姿态Mosaic把四张图拼成一张对提高小物体检测和遮挡鲁棒性非常有效HSV扰动亮度、对比度增强用来模拟白天强光、夜晚昏暗环境随机遮挡模拟多个垃圾叠放时互相遮挡的情况。我还尝试了MixUp两图融合但在YOLOv5上提升不明显反而让部分易混淆类别的特征更糊了最终没有用。这里也想提醒一句数据增强不是越多越好每种增强都是在制造新样本和改变样本分布之间找平衡必须用实验说话而不是凭感觉堆配置。3. 训练关卡YOLOv5从启动到收敛的调参记录3.1 迁移学习与训练配置我没有从零开始训练模型。虽然垃圾分类是一个比较垂直的领域但通用的目标检测特征边缘、纹理、物体形状是相通的所以直接加载在大型通用目标检测数据集上预训练好的权重作为起点然后在大规模数据集上继续微调。这样的好处非常直接收敛快小数据集下不容易过拟合泛化能力也明显好于从零训练。具体的训练配置我列在这里供参考配置项我的设定说明输入分辨率640x640优先保证小目标能看清Batch Size16根据显存调整梯度更新稳定Epochs100-150早停生效防止无效训练优化器SGD初始学习率0.01带动量配合余弦退火学习率策略余弦退火后期更平滑收敛预训练权重通用目标检测预训练权重迁移学习加速收敛3.2 训练过程中的指标观察训练过程中我最关心的指标不是Loss曲线而是三个东西mAP0.5、mAP0.5:0.95、以及每个类别的AP。mAP0.5是框是否大致框对的指标mAP0.5:0.95则更严格对框的精确位置也更敏感。垃圾分类这种应用场景框稍微偏一点其实没那么致命真正致命的是类别认错所以我会重点看每一类的AP尤其是易混淆类别的AP波动。在训练初期mAP涨得很快这是迁移学习的正常表现。到了60个Epoch左右曲线开始平缓如果继续训练会有出现过拟合的迹象——验证集mAP不再上升甚至有轻微下降。这时我开启了早停机制让模型自动在最优节点保存权重而不是傻傻跑完所有Epoch。3.3 卡在收敛不上/过拟合的处理方法我在这套项目里遇到过两类典型问题。一类是Loss降不下去最后发现是数据里干净背景的图太多模型学成了看到频繁出现的背景纹理就认为有目标另一类是验证集指标比训练集差一大截典型的过拟合信号。处理方法是组合拳加强Mosaic比例来增加样本多样性加大数据集中困难样本的比重同时把一些正则手段比如权重衰减稍微调大一点。还有一个很容易被忽略的细节验证集图片不要有数据泄露。我最初做训练/验证切分时用的是随机切分导致同一个物体出现在训练集和验证集的不同图片里验证指标虚高。后来改成按场景切分即同一批次拍摄的照片要么全进训练集、要么全进验证集指标才变得真实可信。4. 精度瓶颈的破解尝试注意力、检测头与损失函数的三路实验4.1 初版模型的瓶颈定位初版YOLOv5模型在验证集上的mAP0.5大概是87%左右看起来不低但分析每类AP之后发现问题很明显塑废弃电池、玻璃碎片、烟头这几类的AP低于70%。这些类别要么体积小、要么外观和背景接近、要么样本数量少。我于是确定了三个改进方向也对应做了三组对比实验。4.2 改进一在Backbone与Neck加入注意力模块第一路改进是引入注意力机制。思路很直接让模型在提取特征时更注意前景物体的区域减少无关背景干扰。我在Backbone的C3模块之后和Neck的上采样路径里插入了轻量级注意力模块只增加了一点点参数量和计算量但实测下来颜色与背景接近的类别比如透明塑料袋灰色水泥地旁的烟头的AP有了明显提升。这组实验让我意识到注意力模块在普通目标上提升有限但在目标和背景难区分的场景里效果显著。垃圾识别正好大量存在这种场景所以这个改进方向是有实际价值、有说服力的。4.3 改进二针对小目标的检测头与特征融合第二路改进针对小目标。YOLOv5本身有多个检测层分别对应大、中、小目标。但垃圾场景里小目标有其特殊性不是远处的小而是近距离照片里的小块物体比如一颗药片、一个瓶盖、一节电池。这类目标在原图上可能只占几十个像素容易被下采样后丢掉信息。我采用的方案是增加一层面向更小目标的检测头并让浅层高分辨率特征图在Neck中参与更早的融合。代价是推理速度和显存占用略有上升但小目标类别的AP涨了大概4-5个百分点这个代价我认为非常划算。4.4 改进三损失函数层面的样本难易度优化第三路改进是在损失函数上做文章。YOLOv5默认的损失函数对所有正样本框一视同仁。但在垃圾数据集里很多框对应的物体本身就很难认塑料瓶被压扁、纸张揉成团、多个垃圾叠压在一起。如果让模型把所有样本都学得一样用力那些简单的大目标会主导梯度困难样本学不好。我改成带难例感知机制的损失策略让模型对困难样本的损失给予更大权重。实际操作中这种策略有一个风险如果权重调太大训练初期模型会被噪声样本带偏。所以我采用了一个自适应策略在训练后期模型已经具备基础能力时再逐渐加大对困难样本的权重。这组实验的收益是又难又小的类别AP继续提升同时简单类别没有明显回退。4.5 三组改进的实验结果对比方案mAP0.5mAP0.5:0.95小目标类AP推理耗时(ms)基线YOLOv587.4%63.8%68.9%8.2注意力模块89.2%65.4%73.5%8.7注意力小目标检测头90.6%67.2%78.1%9.6注意力小目标检测头损失函数优化91.5%68.7%80.3%9.8最终方案相比基线mAP0.5提升了约4个百分点小目标类AP提升了超过11个百分点。这些数据在自己的数据集上都做了多次重复实验取的是稳定的平均结果。需要说明的是不同人自建的数据集不同绝对数值没有可比性但注意力机制解决背景干扰、小目标检测头解决小物体、损失函数优化解决难例这三个方向的增益逻辑是通用的。5. 把不同模型放在同一考场模型对比实验设计5.1 对比模型的选择与公平性做模型对比实验最重要的事情只有一个保证公平。我踩过这个坑——一开始对比时不同模型用了不同的训练策略有的训练了50个Epoch有的训练了150个Epoch得出来的结论完全不可信等于自嗨。后来我复盘并重新设计了实验所有模型都在我前面说的同一套垃圾分类数据集上训练使用一致的输入分辨率、Batch Size和训练Epoch都采用相同的迁移学习策略加载各自官方预训练权重评价指标统一使用mAP0.5、mAP0.5:0.95和每类AP。5.2 对比结果与结论当时我做对比实验除了验证YOLOv5的改进效果还想回答一个问题这个项目如果用其他主流模型来做效果会不会更好我分别测了另一款流行的轻量级单阶段检测模型以及把YOLOv5的Backbone替换成一种更高精度的分类网络结构。结果很有意思轻量级单阶段模型在推理速度上普遍比YOLOv5快但小目标类别的AP普遍低不少说明它更适合目标大而少的场景高精度Backbone确实把mAP提升了一截但推理耗时的增加也很明显部署到实时摄像头场景时会有点吃力YOLOv5的改进版本在精度-速度-部署难度这个三角里是最均衡的。这次对比实验的真正价值不是证明谁比谁强而是让我意识到模型选型永远没有绝对最优只有针对你的真实场景和约束条件数据规模、设备算力、实时性要求、部署流程做取舍后的最合适方案。6. 从离线权重到实时检测系统系统原型部署之路6.1 系统架构与模块设计训练好的模型只是一个离线权重文件距离一个垃圾分类检测系统还差得很远。我搭建的系统原型分成了四个模块图像采集模块支持图片文件、视频文件、USB摄像头实时画面三种输入源目标检测推理模块加载训练好的权重对每一帧/每一张图做目标检测输出每个物体框的类别和置信度分类规则映射模块将具体物品种类映射到厨余、可回收、有害、其他四类同时输出一条置信度阈值过滤规则框置信度低于阈值的直接丢弃不进入分类结果界面展示模块实时显示检测画面、识别类别、分类结果和帧率信息。这个架构最大的好处是模块之间解耦。后面如果要把规则从四分类改成更细的细分类我只需要改第3个模块如果要换模型只需要换第2个模块里的权重加载代码。系统的可持续迭代性比单一大脚本强太多了。6.2 摄像头实时推理的实现细节摄像头实时推理要比处理单张图片复杂那么一点。核心难点在于FPS控制和稳定性。我最开始直接在摄像头回调里逐帧做完整推理结果帧率只有10fps出头画面看起来非常卡顿。后来做了一层优化推理模块采用双线程最新帧替换策略——采集线程持续拿摄像头画面并放进缓冲队列推理线程从队列里取最新的一帧来检测丢弃积压的旧帧。这样保证界面上永远显示的是最新的检测结果而不是处理不完的堆积帧。另一个细节是置信度阈值的处理。离线评估时阈值定在0.25能保证mAP最高但在实际摄像头场景中偶尔出现画面模糊、快速抖动导致的误检框。我最终把显示阈值提高到了0.45牺牲了一点点召回但用户看到的识别结果非常干净。所以不要迷信离线评估的最佳阈值部署时一定要按实际场景重新调。6.3 推理加速的实测方案关于推理速度我做了三组实测原始PyTorch直接推理、转ONNX用CPU推理、再转半精度/量化推理。结果用表格记录如下推理方式单帧耗时FPS说明PyTorch GPU直接推理9-10ms约40灵活便于调试ONNX CPU推理25-35ms约30无GPU设备也能跑半精度/量化推理5-6ms60部署最佳选择对于实时的垃圾分类箱原型来说GPU版本的PyTorch推理其实已经够用但如果要部署到边缘设备上就一定要走模型转换和量化这条路。值得注意的是量化会有一定精度损失考虑到垃圾识别对类别不准很敏感我选择保留少量精度损失但换来更高帧率的方案然后通过提高显示阈值来控制误检。7. 血泪经验那些教程和权重文件不会告诉你的坑7.1 一个标注错误毁掉一个类别我在项目中期发现废电池这个类别的AP突然从80%掉到60%排查了半天原因是某一批标注里把纽扣电池和硬币的标签完全标反了。深度学习模型对标注错误非常敏感尤其是小类别几十个错误标注就足以干扰学习。所以我在第二轮数据清洗时建立了一套交叉校验流程每类抽取一部分预测错误的样本人工判断是模型学得不对还是标签本身标错持续迭代修复。7.2 验证集漏雨会给你虚假的信心前文提到过按场景切分替代随机切分是数据划分的关键修正。随机切分时同一场景连续帧里的同一个塑料瓶可能出现在训练集和验证集各一张导致验证集指标虚高。切分方式改掉之后模型的真实泛化能力才暴露出来。如果你发现模型在验证集上mAP很高但放到真实环境里完全不能打第一个要检查的就是数据划分是否严格。7.3 部署分辨率与训练的差异还有一个实际部署中容易栽的跟头训练时用的是640x640的输入但摄像头采集的画面是1920x1080甚至更高。如果直接把长边resize到640而宽高比没有做等比例处理目标框坐标映射回来的时候会偏。正确的做法是做一个等比例缩放灰色填充的letterbox处理推理完成后把坐标等比还原回原始画面。这一步我在第一次做摄像头联动时没有处理导致框和实物对不上看着极度尴尬。7.4 给后来者的建议如果让我给准备做类似AI项目实战的人一条最核心的建议把70%的时间花在数据和评测的可靠性上而不是模型的堆叠上。一个干净、可靠、无泄漏的数据集和一个公平、稳定的验证评价体系才是让所有算法改进有说服力的前提。模型结构上的各种改进在数据不干净的前提下效果都是不可信的。最后再分享一个小技巧保存每一轮训练的权重时一定要同时保存对应的模型结构配置、超参数列表和训练日志。我中途差点把三种改进方案的配置搞混幸好有完整的版本记录才把结果对齐。这个习惯后来在写对比实验结论时帮了我大忙不然真到整理数据的时候才发现当初怎么看都统一不了那才是真正的灾难。

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价 →
↑