排水管道病害智能辨识算法研究
城市地下的排水管道跟人体血管很像,平时看不见摸不着,一旦堵了、破了、错位了,轻则路面积水,重则地面塌陷。过去我做过几年工业视觉检测,一直跟“给设备看片子”打交道,去年开始接触市政排水管道检测,才意识到这个场景比工厂质检难多了。光线忽明忽暗、镜头带水雾、管内淤泥挡视线,病害形态千奇百怪,传统的图像处理规则根本写不全。
这个项目的标题是“排水管道病害智能辨识算法研究”,简单说,就是用深度学习目标检测模型,自动识别CCTV管道检测机器人传回来的视频画面,把破裂、变形、树根侵入这类病害在画面里框出来,替代人工一遍遍看录像的重体力劳动。适合正在做视觉算法落地、智慧城市方向,或者搞水务信息化的人参考。我自己从数据采集一路做到边缘端部署,踩过不少坑,这里把思路和实操经验完整梳理一遍。
1. 项目概述:给城市排水管网“看片子”
1.1 为什么这个课题值得做
排水管道内检测目前的主流方式是CCTV检测,就是把带摄像头的机器人放进管道里,一边走一边录像,检测人员回看视频找病害。听起来简单,做起来非常痛苦。一段三四公里的管网,录像可能有十几二十个小时,检测员对着屏幕一帧一帧看,眼睛很快就花了。而且病害的判断标准带有一定主观性,同一个画面,上午和下午看可能结论都不一样。
更麻烦的是病害本身形态多变。破裂是裂缝带泥土渗入,变形是管口由圆变扁,树根侵入则是细根从接口缝隙钻进去,颜色和周围淤泥混在一起。这些特征在图像上高度相似,边界模糊,传统图像处理算法靠边缘、灰度、纹理这些底层特征很难稳定区分。我最早试过用边缘检测加形态学规则去筛裂缝,结果水面波纹、管壁划痕全被当成病害,误报高到没法用。
所以这个项目的核心价值,是把卷积神经网络引入到管道病害辨识里,让模型自己学习“什么看起来像破裂”“什么看起来像变形”,而不是人类一个一个去写规则。实践下来,目标的检测精度能稳定在90%以上的mAP,单帧推理耗时在嵌入式设备上控制在100毫秒以内,这才让“自动出检测报告”成为可能。
1.2 项目目标与技术边界
立项时我跟团队定了一个很务实的范围:不做12类全量病害识别,先抓三类最影响结构安全的病害,分别是结构性破裂、管道变形、树根侵入。再加上一项功能性风险,就是水面异常覆盖导致的检测盲区,用来提示检测员是否需要返工。把目标缩小之后,数据标注、模型训练、现场验证的节奏一下子清晰起来。
技术路线上,我们锁定的是基于深度卷积神经网络的目标检测框架,而不是语义分割或实例分割。原因很直接:排水管道病害检测的上游是视频巡检,下游是维修工单,业务方需要知道“什么病害、在哪个位置、大概多严重”,不需要像素级轮廓。目标检测给出的矩形框足够支撑后续的量化评估,而且标注成本和训练成本都低得多。关于选型细节,后面我会专门展开。
2. 先抓好数据,否则算法就是空中楼阁
2.1 CCTV影像数据从哪来、怎么变成训练集
数据是这个项目里花时间最多的一环。合作单位提供了往年几十个项目的CCTV检测录像,格式大多是MP4和AVI,分辨率从720p到1080p不等,帧率25fps和30fps混合。我第一次打开这些录像的时候,心里凉了半截,画面要么黑漆漆,要么白花花一片,还有大量机器人原地抖动造成的模糊帧。
数据清洗是第一道关键工序。我写了一个抽帧脚本,按每5秒抽1帧的策略把长视频切成图片集,然后用了两人交叉复核的方式筛掉三类废图:完全失焦的、被淤泥完全遮挡的、重复度极高的。清洗完大概留下8000多张有效图片,这个量训练深度学习模型只能算及格线,但配合后续的增强策略完全够用。
第二步是标注。考虑到后续换模型格式方便,我统一用的COCO格式JSON,用标注工具逐框标出目标位置和类别。标完之后做了一次一致性检查,同一张图让两个人分别标,比对框的重叠度,低于0.7的重新讨论,确保标注标准统一。特别是“变形”和“破裂”这两个类别,人眼都容易混淆,我制定了细则:管口整体失圆算变形,局部出现贯穿性缝合并伴有土壤或地下水渗出迹象才算破裂。
2.2 标注规范与病害分类体系的取舍
标注不是把框画出来就完事,分类体系直接决定模型能学到什么。最初的检测规范里有12类病害,但我分析完现有数据后发现,很多类别样本量只有几十个,比如渗漏、腐蚀,训练出来也是过拟合,没有实用价值。我干脆砍掉低频类,只保留四类,其中树根侵入因为形态特征相对独立,检测效果最好。
标注时还有个容易忽略的细节:病害框的大小差异巨大。破裂裂缝可能只占图像面积的1%,树根却可能占据半个画面。这种尺度极端不平衡,后面会严重影响模型对小目标的学习。我的处理办法是把标注框的面积、宽高比都做了统计,按长尾分布给每个尺度区间设计了不同的采样权重,小目标在每次训练迭代里被多抽样几次。
2.3 样本不均衡的应对和增强策略
数据集的原始分布很不均匀,树根样本大约3000个框,破裂只有1200个框,变形只有600个框。直接训练的话,模型会对树根类严重偏置。增强策略我用了三层:
- 第一层是通用的,随机翻转、旋转90度、HSV颜色扰动、高斯模糊,让模型对光照和角度变化更鲁棒。
- 第二层是针对管线环境的,模拟水滴效果、随机亮度遮挡、加入噪声条纹,这些操作让模型知道病害本身不等于环境纹理。
- 第三层是小目标复制粘贴,把破裂和变形的小尺寸样本裁剪出来,按一定规则贴到无病害的背景图上,同时生成对应的标注框,这一步对提升小目标召回率非常有效。
增强不是越多越好。我一开始加了大量随机裁剪,结果模型把很多背景纹理学成了病害特征,误报又抬高了。后来把裁剪比例限制在0.5到1.5倍之间,只做轻微缩放,误报立刻降下来。增强策略和超参数一样,需要在验证集上反复调,别一股脑全堆上去。
3. 模型选型与算法设计思路
3.1 为什么最终选目标检测而不是分割
其实立项时也有人提过用语义分割做裂缝检测,理由很直观,裂缝是细长的,矩形框会框进大量背景,看起来不「精细」。但我仔细推演了一下,最终否定了分割路线。
首先,精细不等于实用。下游养护单位拿到一张裂缝分割图,往往不知道怎么施工,反而是和目标检测配套的病害等级判定能直接对应修复方案。比如破裂病害的框宽与管径的比值,可以作为严重程度的量化指标。其次,分割标注成本高到离谱,裂缝像素级标注一张图可能要半小时,而目标检测标注只要十几秒。考虑到我们只有8000多张图,分割方案数据量完全不够。
在目标检测框架内部,我对比了两条路线:两阶段的Faster R-CNN系列和单阶段的YOLO系列。Faster R-CNN精度高,但推理速度在嵌入式设备上不够用;YOLOv8在精度和速度的平衡上更优,所以我最终以它为基础。
3.2 主干网络与检测头:YOLOv8做了哪些定制
直接用YOLOv8s预训练权重跑了几轮,mAP只有65%左右,瓶颈主要出现在两个地方:一是小尺寸裂缝容易漏检,二是干扰物误报多。针对这两个问题,我做了三项定制:
- 结构上将主干网络默认的C2f模块替换成可变形卷积版本,让感受野能贴合病害的细长形和不规则形,实验显示破裂类的AP提升了大约5个百分点。
- 加入一个针对小目标的P2检测层。P2层的特征图分辨率更高,包含更多空间细节,小裂缝的召回率明显改善。代价是计算量增加,后面我用其他剪枝手段抵消了。
- 在颈部网络部分嵌入了注意力模块,让模型在融合多尺度特征时更关注病害区域,削弱背景水渍、管壁纹理的影响。
这些改动如果并行上,训练收敛变慢而且指标不升反降。我后来是逐个模块加,每加一个就在验证集上评估一次,相当于做了一次消融。最后固定下来的组合是“可变形C2f+P2头+注意力”。
3.3 训练策略与超参数调优细节
训练策略我们分两阶段走:先用通用目标检测数据集把模型预训练到收敛,再把自建的管道病害数据接进去微调。微调时冻结前10层骨干网络,只训练检测头和高层特征层,这样避免了小数据集训不动深层网络的问题。
超参数方面有几个关键数值值得记录。初始学习率设的是1e-3,使用余弦退火策略,warmup轮数设了3个epoch。batch size在单卡上设为16,图像输入尺寸是640乘640。数据增强概率统一是0.5。这些数值没有哪个是玄学,全部来自小规模网格搜索,比如学习率从1e-4到1e-2都测过,1e-3在验证集上mAP最高。
损失函数我用了默认的边界框回归损失加分类损失,但对各类损失权重做了调整。因为变形类样本太少,权重从0.5提到了1.2,代价是树根类的精度略降,但整体mAP反而高了一点。如果做这类项目,有权重分配需求,建议在训练日志里打上每一类的AP曲线,别只盯总mAP。
我还用了早停机制,设定验证集mAP连续20个epoch不增长就停止训练。最终模型训练到第180轮左右收敛,验证集mAP稳定在90.6%,其中树根类最高到了95%,破裂类91%,变形类87%。速度上,在嵌入式设备上用TensorRT INT8量化后,单帧推理约85毫秒。
4. 部署落地与工程化改造
4.1 算力约束下的推理加速
训练好模型只走完一半路,真正麻烦的是把模型塞进现场设备。管道检测机器人上往往没有高端GPU,我们用的算力平台是一块英伟达嵌入式板卡,INT8算力大约几十Tops,大概相当于一个入门级独立显卡的几分之一。
推理优化首要任务是模型轻量化。我先把输入分辨率从640降到544,mAP只掉0.8个百分点,推理时间缩短了约20%。接着做通道剪枝,对颈部网络里贡献小的通道做稀疏化,剪掉30%的通道,再用知识蒸馏从原来的模型里恢复精度。
然后是TensorRT加速。从PyTorch导出ONNX,再转TensorRT引擎,用INT8量化。这个环节踩了很多坑:量化校准集选得不好,导致树根类掉点严重;每类样本数量要均衡,选500张代表图做校准,最终各类别精度损失控制在2个百分点以内。量化后单帧推理速度稳定在85毫秒左右,达到实时要求。
4.2 检测结果后处理与报告联动
模型输出的裸结果不能直接用。CCTV录像里有大量连续帧,同一处病害会连续出现几十次,如果每帧都报警,报告会炸掉。我写了一个时间窗口聚合模块:病害框和类别在连续N帧内保持高置信度,合并成一个事件;置信度低于阈值的框直接丢弃;事件去重后,取那个打到最高置信度的一帧作为代表帧。
聚合之后还要映射到物理位置。机器人录像上有距离计数,每帧对应一个里程值,我用插值算法把病害事件对应到具体管道桩号区间。这样下游生成的检测报告可以直接标注“管线桩号K0+115至K0+119存在破裂病害”,业务侧不需要看原始视频就能派单。
报告联动这部分,我做得比较朴素,就是把结构化结果导入一套内部定制的表格模板,自动生成病害统计表。包括每类病害的数量、平均置信度、位置区间分布等。为了让误检在报告阶段可控,我在模板里增加了“AI置信度低”标签,让审核员优先看这些疑似区域。
4.3 现场运行稳定性保障
工控设备在潮湿、颠簸环境下长期运行,程序稳定性比功能更重要。我在部署时给自己定了几条硬规矩:
- 程序必须支持断点续跑,现场断电后重启,能从最近一个已处理位置继续,而不是从头开始。
- 每个视频文件的检测结果实时写盘,不能攒到最后一批输出,防止进程崩溃丢掉全部中间结果。
- 每处理完一段视频,计算并打印一次平均帧耗时和检测事件数量,如果连续5段视频推理耗时异常,自动重启推理引擎。
还有一处经验:夜间检测现场的光照非常不稳定,机器人前灯照在管壁上的角度变化会导致图像整体偏亮或偏暗。我在离线测试时专门准备了一批“夜间现场”测试集,模型上线前用它做一次回归测试,防止日间数据训练出的模型在夜间场景上失灵。这种测试集最好跟训练集严格分开,批次靠后标定更稳。
5. 常见问题与排查实录
5.1 水面高光把模型“带偏”了
第一次现场试运行时,我发现模型把很多水面高光区域框成了破裂。看训练集才发现,正样本里有一小部分破裂图片正好处在高光照明条件下,模型学到了“亮斑等于裂缝”这种错误关联。这不是模型笨,是数据集里存在虚假相关。
针对这个问题我做了数据层面和策略层面的双重调整。数据层面,用数据增强生成了一批“高光但无病害”的负样本,加到训练集里。策略层面,对破裂类的置信度阈值单独提高,从0.25升到0.45,误报明显下降。比较关键的一步是可视化模型注意力热力图,看到模型确实聚焦在亮斑区域后,我才坚定地走负样本增强这条路。
5.2 小目标裂纹总漏检
项目开始时破裂类漏检主要集中在小裂缝,尤其是宽度只有几个像素的细裂纹。我复盘发现,640分辨率的输入在两次下采样之后,小裂纹的特征已经模糊得几乎不可辨。
加了P2检测层之后,小目标召回率提升了一截,但还做不到完全满意。我又试了测试时增强(TTA),把输入做小幅缩放和多尺度推理,最后把结果合并。TTA有效但也有成本,推理时间近乎翻倍。最后折中方案是:线上默认单尺度推理,当检测到疑似区域但置信度低于阈值时,对该区域做一次局部放大再识别。这个“局部二次检查”思路,既保住了速度,又捡回不少漏检。
5.3 类别不平衡让变形缺陷“隐身”
变形类因为样本少,训练初期AP只有50%左右,模型几乎不认识变形。我做了几个动作:把变形类的数据增强强度单独加大,让同一张图产生更多视角变化;把损失权重上调二倍;又把一部分树根类数据随机降采样,控制总数平衡。
跑完新一批实验,变形AP从50%拉到了77%,但直接对比树根类还是低不少。项目组最后在结论里如实标注了各类别可靠度差异,这也算一种专业态度。如果后续能把变形类的实际样本补到2000个以上,AP应该还有上升空间。
5.4 模糊帧成了误报重灾区
CCTV机器人在管道里边爬边转,运动模糊非常常见。模糊帧上,管壁纹理被拉成条状,模型时常把拉长的纹理当作裂缝。
解决思路是从源头做文章:推理前加一个清晰度评分模块,计算图像拉普拉斯梯度方差,低于阈值就直接标成“模糊帧,不做检测”。这样可以避免把不可靠的结果混进统计。有段时间我担心会漏掉“真实病害但恰好在模糊帧出现”的情况,后来跟检测工程师沟通,他们对模糊帧原本就不做人工判读,所以策略完全符合业务习惯。
5.5 快速排查速查表
我把调试期间那些高频问题整理成一个速查表,给后来接手项目的人参考:
| 现象 | 可能原因 | 验证方法 | 处理建议 |
|---|---|---|---|
| 误报集中在亮斑、水迹 | 数据中有虚假相关 | 查看注意力热力图 | 针对性增加负样本 |
| 小尺寸裂缝漏检 | 特征图分辨率不足 | 按框面积统计AP | 添加P2检测层或二次放大 |
| 某类病害识别率明显低 | 样本不均衡 | 看各类别损失曲线 | 调整损失权重、增强强度 |
| 模糊帧误报多 | 分辨率退化 | 查看测试集模糊占比 | 前置清晰度过滤 |
| 量化后精度大跌 | 校准集不均衡 | 逐类精度对比 | 重建量化校准集 |
利用这个表可以少走很多弯路。每个项目开始时先跑一版小模型,把这些问题快速筛一遍,再集中资源解决两三个最大头的问题,比憋大招更高效。
我个人在实际操作中最深的一点体会是:做管道病害辨识这类垂直场景算法,模型骨架只是其中一个环节,数据规范、业务约束、部署优化这三样往往更消耗精力。先跑通一个高价值病害的闭环,让现场团队信任自动检测结果,再逐步扩展类别,比一开始就追求全类型识别稳妥得多。在穿梭着淤泥和水汽的管道图像里,用网络去捕捉裂缝和变形的蛛丝马迹,这件事本身就足够有意思,后续我会继续在这条路上把模型做得更轻、更准、更贴合一线作业。最后分享一个小技巧:在训练这类严重尺度和类别不平衡的小样本数据时,每训练十几个epoch就抽一次验证集可视化结果,不要只在最后看指标。那些被漏检的裂缝和误报的水波,往往比mAP曲线更能说明下一步优化方向。