☰
深度学习工业表面缺陷检测实战:从数据集构建到部署优化
2026/10/20 4:35:53 网站建设 项目流程

前两年接了一个3C结构件外观检测的项目,真是把我对工业质检的理解彻底翻了一遍。传统视觉方案在PCB焊点、端子间距这类结构固定、背景单一的场合,确实是又快又稳;可一旦碰上金属外壳表面的划痕、印刷品上的飞墨、薄膜上面的气泡,规则参数调得再好,还是被现场产线上的杂色背景和缺陷形态变化打得满地找牙。后来我们团队把整套方案切换到深度学习路线,从图像采集、数据标注、网络训练一路做到工控机上的推理部署,才琢磨清楚一件事:基于深度学习的工业表面缺陷检测,难的不是算法本身,而是怎么让算法在真实产线的节拍、光线、样本分布下稳定工作。

这篇文章我不打算写成一个技术综述,而是按项目复盘的方式,把整个研究过程里最关键的几个决策点和踩过的坑讲清楚。适合刚接触工业视觉、又想用深度学习代替传统规则方案的工程师参考。整体会覆盖数据集怎么攒、网络怎么选型、训练细节怎么调、最后怎么带着精度损失控制把它装进产线。

1. 从传统视觉的极限说起:为什么缺陷检测必须换思路

1.1 表面缺陷到底长什么样

工业产品表面缺陷很难用一个统一概念概括。对于我这几年经手的项目,常见的可以分成几类:

  • 硬性划伤:比如金属外壳上的刮痕、玻璃表面的线状划伤,特征是长条状、边缘清晰、方向随机。
  • 点状缺陷:包括气泡、麻点、崩边、砂眼,特征是尺寸小,对比度可能很低。
  • 区域类异常:水渍、油污、氧化色差、涂层不均,边缘模糊,和背景的灰度差别不稳定。
  • 纹理异常:编织物、拉丝金属、皮革表面出现的纹理断裂或者发花,这类最讨人厌,因为正常纹理本身就有很大的随机性。

传统方案对付这些缺陷时,常用的手段无非是灰度阈值分割、形态学处理、模板匹配、频域滤波。听起来不难,但产线上的实际情况是:光源稍微老化一点,灰度就漂移;产品型号换一批,纹理基准就变;缺陷对比度稍微接近背景,阈值就失灵。一个案子调三个月勉强能跑,下一个相似产品又得从头来过。

缺陷类型传统方案适用性失败的关键场景
结构尺寸测量好几乎不需要深度学习介入
规则复杂背景的硬划伤中低背景有花纹、划痕深浅不一
低对比度气泡/麻点低和材质反光混在一起
纹理异常差正常纹理本身就无规律

1.2 深度学习在质检任务里的真正优势

很多人以为深度学习只是把分类做得更准,实际上在表面缺陷这个场景里,它最大的价值是省去了人工设计特征的过程。传统算法要求你事先定义“什么样算缺陷”,而卷积网络只需要从标注样本里自动学出一套对光照变化、形态变化都更鲁棒的特征表达。同一个模型,划痕可以是水平、垂直、弯曲、断续的,只要训练数据能覆盖,网络就能把特征抽出来。

理解到这一层以后,项目的重心就变了:不是说搞一个多么复杂的网络结构,而是确认数据链路是否可靠、任务范式是否匹配、部署环境是否允许。我们当年在这个环节的错误是过于迷信新出的网络结构,换了好几个骨干网络,结果发现精度上限根本没被模型结构卡住,反而被样本质量和标注一致性牢牢焊死。

2. 缺陷样本从哪来:数据集构建是真正的硬骨头

2.1 打光质量决定了数据的天花板

我见过不少项目,上来就谈网络选型,完全忽略图像采集。实际上,深度学习再怎么强大,也是对输入图像做映射;如果光源布局不对,缺陷在图像里压根没有可区分度,后面的所有工作都是白做。

以金属外壳检测为例,我们试过好几种光源组合,最后用的是低角度环形光加同轴光的组合。低角度环形光的好处是能让浅表划痕产生明显的散射,让缺陷在暗背景下亮起来;同轴光则负责均匀照亮整体,避免环境反射带来的假纹理。对比之后我们发现,同一个划痕在条光下有时看起来像一条细缝,在低角度光下却变成一条明显的亮线。这个选择直接决定了模型要学的东西是否存在。

打光试验一定要多拍几张一比一的产线样品图放到训练环境里看直方图和纹理分布,不能只靠肉眼看。很多缺陷在显示器上能看见,不代表传感器采集到的灰度差异足够明显,采集系统的动态范围和镜头分辨率也会影响最终效果。

2.2 标注的颗粒度与一致性

表面缺陷检测需要什么级别的标注,取决于你要什么级别的输出。我们项目早期只做整张图的好/坏分类,标框就够用;后来产线工人反馈只告诉“这块零件有问题”不够,他们想知道问题在哪里,因为同一片产品上可能有多个缺陷,而且翻修工位需要缺陷位置信息。最终我们切换到像素级标注,用分割的思路做。

像素级标注有个容易被忽略的成本问题:标注员对“边界在哪”的判断不会完全一致。两个标注员标同一个气泡,一个稍微向内收,另一个稍微向外扩,这个差异在训练时会直接变成边界模糊的噪声。我们的解决办法是强制采用统一标注规范,缺陷边界延伸到像素值开始变化的过渡区中心线,同时对每个标注结果做二次复核,凡是分歧大的样本单独拉出来讨论。

缺陷类别少的时候,人工标注还能扛住。如果缺陷类别达到十种以上,品类之间的混淆就会让标注成本直线上升。这时候要优先区分“哪些缺陷必须分开”,比如一个叫脏污、一个叫划伤,产线处理方式完全不同,就必须分开标;而像细划痕和深划痕这种只是程度差异的,建议合并类别,减少标注负担,模型也更容易学。

2.3 真实样本稀缺时怎么破局

工业场景里最常见的尴尬,是缺陷发生概率极其低,可能一万个产品里面只有二十个带缺陷,而且要凑齐全类型缺陷得攒好几个月。项目上线节奏根本等不了。

我们当时用了三条路线并行凑数据:

  • 第一条是真实样本全覆盖,把产线攒下来的历史不良品全部重新拍照入库,能凑多少是多少。
  • 第二条是规则合成,在正常产品图上人为叠加模拟缺陷。划痕就用带灰度变化的多段线加运动模糊,气泡就用不同直径的椭圆叠加明暗边缘,脏污就用噪声叠加扩散模糊。合成的目标不是让图像变得多逼真,而是逼迫网络学习“正常表面和局部异常之间的对比关系”。
  • 第三条是半监督思路,可以先拿大量无标注的正常样本训练一个异常定位模型,学出正常纹理的分布,再用少量真实缺陷样本做微调,让网络知道哪些偏移才是真正需要报警的缺陷。

合成样本有个诀窍:合成的比例不能太高。如果训练集里百分之八十都是合成缺陷,模型会不自觉依赖合成缺陷的某些特征,比如边缘过于锐利、对比度过于均匀,到了真实图像上就频繁漏检。我们最后把合成样本的比例控制在四成以下,再用真实样本兜底,效果才稳定。

3. 网络选型与结构设计:怎么选范式比选模型更重要

3.1 分类、检测、分割还是异常检测

很多初学者拿到项目就直接下载一个开源检测模型跑起来,结果不是精度不够,就是标注和应用场景对不上。选择任务范式之前,必须先回答一个问题:产线需要你输出什么?是需要给整片产品打分,还是需要标出缺陷位置,还是需要算缺陷面积?

我习惯把范式分成四种:

  • 图像分类:输入一张图,输出好/坏。适合数据量小、只需要粗筛的项目,但无法定位。
  • 目标检测:输出缺陷的边界框,能定位,但对不规则缺陷的轮廓描述粗糙。
  • 语义分割:输出像素级类别掩码,最贴合质检需求,因为能准确算出缺陷大小和位置。
  • 异常检测:只在正常样本上训练,通过重构误差或特征距离判断异常,适合正样本极丰富、缺陷几乎不可枚举的场景。
范式标注成本定位能力对缺陷变化的鲁棒性适用场景
分类低无一般快速验证
目标检测中框级良好大尺寸缺陷
语义分割高像素级较好细长划痕、低对比度缺陷
异常检测极低弱定位有限缺陷类型未知

3.2 针对细小缺陷的网络结构上做的改造

表面缺陷里有一类特别难缠:细划痕和针孔。它们的像素占比往往不到整张图的千分之一,直接输进一个分类网络,下采样几次以后特征就基本消失了。我们最后走的是分割路线,但也不是拿一个基础分割网络直接用,而是做了几个关键改造。

第一,输入分辨率不能一味降。为了匹配产线节拍,很多人一上来就把图像缩到几百乘几百,这样速度是快了,但对细划痕是灾难。我们在显存允许的范围内,把输入分辨率保持在一千多乘一千多,配合多尺度训练,让缺陷在原始尺度上有足够像素支撑。

第二,特征金字塔结构非常重要。工业图像里的缺陷大小差异很大,大面积色差需要高层语义特征,细划痕需要底层纹理细节。网络如果只有单层输出,必然顾此失彼。我们采用了带多尺度特征融合的结构,让浅层细节和高层语义能够互补。

第三,注意力机制确实有效。实验里我们发现,在分割骨干后面加一个轻量的通道注意力模块,可以让模型更关注纹理异常区域,尤其在拉丝金属面上,效果提升明显。但要注意,注意力模块会增加计算量,在工控机上部署时要反复测耗时,不能只看精度。

3.3 缺陷类型不可穷尽时,异常检测是备选方案

有一类产品的缺陷连产线质检员都很难定义清楚,今天出现的是一种花斑,明天是另一种。这种情况我们试过用基于特征分布的异常检测方法,原理也不复杂:用大量正常样本训练一个特征提取器,统计正常特征向量的分布范围;推理时,计算新样本的特征和正常分布的距离,距离超阈值就报警。

这个方案的好处是标注成本极低,只需要正常样本。坏处是定位能力弱,而且对光照变化特别敏感,因为光照一偏,整个特征的分布就漂移了。我们当时用了一个折中策略:异常检测做初筛,超阈值的图像再进一个小的分割网络做二次确认和定位,误检率立刻降下来不少。

如果你想快速验证缺陷样本是否够用,可以先跑一个简单的基线:把正常样本和缺陷样本各分一半,用一个小分类网络训练,看看验证集准确率能到多少。如果连这个都做不到,模型结构再复杂都没用。

4. 训练调参里的门道:精度的胜负手在细节

4.1 类别不平衡和损失函数的选择

工业缺陷数据天然不平衡。正常的像素数量可能是缺陷像素数量的几百倍,如果我们老老实实用交叉熵损失训练一个分割模型,模型会倾向于把所有像素都预测成正常,因为这么做的损失就已经很小了。

解决这个问题有几个常用手段。按样本采样比例调整,把包含缺陷的图像在训练时提高采样权重,是一种操作简单但见效快的办法;更彻底的是在损失函数上做文章。分割任务里我们最后用了带Dice项的复合损失,交叉熵负责整体收敛,Dice损失负责缓解正负样本失衡,两者比例大概在三比七到五比五之间,具体要看过杀率和漏检率的接受程度。

分类层的类别不平衡还可以用焦点损失,它给难以分类的样本更高的权重,处理少数类效果好。但焦点损失有两种超参要调,调不好反而掉点,所以我的经验是先做样本加权,不够再上焦点损失。

4.2 数据增强该怎么设计才不帮倒忙

数据增强在缺陷检测里是个双刃剑。过度使用几何增强,比如随意旋转、裁剪,容易把有方向性的缺陷搞得失真,比如划痕本来就有固定的主方向,你把它旋转九十度,在真实产线上几乎不会出现,模型学到反而容易误判。对于有明显方向特征的缺陷,我会限制旋转角度,最多做正负十五度以内的轻微旋转,加一点随机平移和缩放。

颜色增强方面,工业图像的特征是光照稳定,但也意味着模型对光照变化比较脆弱。适度增加亮度抖动和对比度抖动是有益的,但幅度要控制,不然会引入不存在的色块。我们试过把色相做大幅随机扰动,结果金属拉丝面的纹理特征被破坏,误杀率直接翻倍。

还有个容易被忽略的操作:在训练时把正常样本和带缺陷样本按比例混进同一个批次。这样做可以保证每个batch里都有正负样本,梯度更新方向更稳定,而不是出现某些batch全是正常图、某些batch全是缺陷图这种极端情况。

4.3 评价指标和阈值怎么定才贴近产线

模型的评价不能只看准确率。工业质检最怕两个事:一是漏检率,就是有缺陷的产品被当成良品放过去,这种错误的代价很大,可能导致批量客诉;二是过杀率,就是良品被误判为不良品,这会造成返工浪费和产能下降。

我们在项目里定的指标组合是:漏检率必须控制在万分之一以内,过杀率则根据不同产品线控制在百分之三到百分之八之间。算法团队最容易犯的毛病是为了追求过杀率好看而反复调高置信度阈值,结果漏检率悄悄上涨。

这里有一组典型的阈值选择过程:模型输出的缺陷概率是连续的,你需要在这条曲线上选一个切分点。如果阈值设得高,只有非常明确的缺陷才报警,漏检率上升;如果阈值设得低,错杀增加但漏检下降。正确做法是拿一批生产线上真实出现的良品和不良品做统计,画出一条漏检率对过杀率的权衡曲线,再和产线负责人一起选点,不要让算法团队独自拍板。

5. 从实验环境走向产线:部署与推理优化

5.1 模型压缩与推理耗时

训练时我们可以用大模型和高端显卡慢慢磨,到了产线部署阶段,面对的往往是一台工控机,用的可能是低功耗显卡。我们的模型最初单张图像推理耗时接近两百毫秒,完全没法跟上产线一秒两三个产品的节拍,迫使我们做了一轮严重的优化。

优化路径基本是三个方向的组合。第一个是知识蒸馏,用一个精度更高的大模型当老师,让小模型去学它的输出分布,这样能在参数减少很多的情况下保住大部分精度。第二个是量化,把模型权重从浮点数压到整数范围,推理速度上去,但精度会有不同程度的损失,有些敏感层量化后误差大,我们会把那些层挑出来保持浮点运算。第三个是运算符融合和缓存优化,把相邻的计算合并,减少中间结果的读写。

量化后的精度评测不能只看整体指标,要特别关注细划痕。我们踩过一次坑,INT8量化后整体分割准确率只掉了零点几个百分点,看起来完全没事,结果细划痕这一类缺陷的检出率掉了一大截,因为细划痕的特征幅度小,量化引入的噪声影响相对更大。后来重新设计了量化校准集,把大量的细划痕样本塞进去,问题才缓解。

5.2 产线节拍下的流水线设计

理想状态下,相机拍完一张图,送入模型推理,返回结果,整个流程应该在几百毫秒内完成。但实际部署时,要考虑图像传输、预处理、推理、后处理四个阶段之间的衔接。

我们的做法是把相机采集和图像推理做成两条并行的流水线:相机在采集下一张图的同时,推理线程在处理上一张图。这里有个容易被忽略的点:推理线程不能被图像传输的锁卡住,否则节拍就会抖动。我们用了一个固定大小的有界队列,图像采集线程把新帧推入队列,推理线程不断从队列取帧处理,队列满时直接丢弃最旧帧并报警。这一套设计跑下来,生产节拍稳定了很多。

后处理阶段也很重要。分割网络输出的是逐像素的概率图,你要把它转成缺陷连通域,再根据面积、长短比做过滤。小噪声点会在概率图上形成很多小区域,如果每个区域都报警,产线根本没法看。我们会设置一个最小面积阈值和最小置信度阈值,只有当连通域面积超过阈值才判为缺陷,这样能滤掉一部分由相机噪声引起的伪报警。

5.3 人机协作与模型迭代闭环

我现在的观点是:质检模型在产线部署后,算法工作并没有结束,而是进入了一个持续迭代的阶段。新的人机协作复审机制会直接影响模型价值。我们把所有报警图像推送到一个复审界面,质检员可以对报警结果做二次确认,并且把确认结果回传到数据管理平台。

这个复审数据是我觉得整个部署环节里最有价值的部分,因为产线上出现的新异常形态、正常样本的边界情况,都会在这里暴露。我们每两周会用累积的复审数据做一次增量训练,模型性能会随着迭代逐渐提升。

有一点要提醒:增量训练不能只在模型上继续跑几步,很容易出现新数据学好了、老数据又开始遗忘的灾难性后果。我们每次增量训练都会把历史样本按一定比例采样回来一起训练,保证模型对新旧样本都有记忆。

6. 复盘过后最想分享的三条经验

6.1 先搞定相机和光源,再谈算法

如果让我重新做一遍这个项目,我会把更多时间花在图像采集阶段。最后我们发现,很多漏检并不是模型学不会,而是图像里缺陷的对比度根本不够。打光方案没定下来之前,不要急着标数据,更不要急着训练,不然后面所有环节都在为错误的输入做补偿。

光源的验证要放在真实产线环境里做,而不是实验室。现场的环境光、传送带振动、相机曝光时间都会影响图像质量。我们一开始在实验室拍出来的图又干净又均匀,搬上线之后才发现背景里多了很多反光和灰尘,模型误检率大幅上升,只能重新增加预处理环节。

6.2 小步快跑,先跑通再优化

工业项目最忌讳的是一上来就追求完美指标。我们第一次上线只用了最简单的分类模型,先保证产线能跑,让工人习惯系统界面,再一步步升级到分割模型。这个过程虽然看起来绕了远路,但好处是每个阶段都有清晰的可交付物,团队和产线的信任也在逐步建立。

如果一开始就上复杂分割方案,光是标注标准讨论和模型调参就可能拖三个月,产线那边等不起。先把最简单的方案用起来,让数据从产线回流,形成标注、训练、部署、复盘的循环,这才是能持续进步的节奏。

6.3 缺陷检测的最后一道关,永远是人的判断

模型再强,也不建议做成全自动无人值守。工业缺陷的形态太开放,总有模型没见过的类型。我把最终方案设计成了两个档位:模型置信度高的缺陷直接自动拦截,置信度在中间地带的结果推送到人工复审界面,由质检员做最终判断。这个策略在项目推广阶段特别有用,因为工人不会盲目信任一个黑盒模型,而人工复审又给了他们参与和修正的机会。

等到累积了足够的复审数据、模型确实稳定以后,再把人工复审的比率逐步降下来。最后我们实际跑下来,自动拦截率占到了全部报警的大约八成,剩下两成需要人工扫一眼,既保证了漏检率底线,也让产线愿意持续用这套系统。

深度学习做工业表面缺陷检测这件事,本质上不是一个纯算法问题,而是数据、算力、现场工程三者协同的系统工程。只要把数据链路和部署闭环想清楚,哪怕用的网络结构不是最时髦的,产线效果也一定不会差。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询