在电子制造行业摸爬滚手的这些年,我经手过的视觉检测项目少说也有几十个,但PCB电子板卡的一致性检测始终是个让人既头疼又上瘾的领域。头疼在于它牵扯的变量太多——光照、位姿、元件批次、焊点反光,稍微一个条件波动,检测结果就能给你上演一出“变脸”;上瘾则在于,一旦你把这条链路跑通了,从图像采集到算法判定再到产线联动,那种把不可控变成可控的成就感,是其他项目很难替代的。这篇内容就是围绕“基于工业视觉的电子板卡一致性检测”这个话题,结合我在Matlab环境下的实际开发经验,把从方案设计到代码落地的完整思路、关键参数计算和排坑记录,一次性讲透。
不管你是刚接触工业视觉的学生,还是已经在产线上折腾过几套检测设备的工程师,这篇文章都适用。我会尽量用“咱们一起调程序”的口吻来写,而不是给你堆一堆看不懂的公式。毕竟视觉检测这东西,理论是骨架,但真正决定项目能不能验收的,往往是那些文档里不会写的细节。
1. 整体方案设计:一致性检测不是简单的“找不同”
1.1 先搞清楚“一致性”到底在测什么
很多人一听“PCB一致性检测”,第一反应就是“拿两张图做差分嘛”。实操过就知道,事情远没那么简单。一致性检测的核心不是“图像不同”,而是“电气性能和生产工艺是否在允许公差范围内保持一致”。一块PCB板卡,哪怕是同一批次、同一台贴片机打出来的,也存在元件本体印刷色差、焊点光泽度差异、丝印轻微偏移等正常波动。真正需要拦截的,是缺件、错件、反件、桥连、虚焊这五类致命缺陷。
所以方案设计的第一步,不是急着写算法,而是和工艺工程师一起定义“一致性”的判定标准。比如某个0402电阻,允许的旋转角度偏移是多少?焊盘上锡面积低于多少百分比算虚焊?丝印字符的OCR置信度阈值设多少?这些参数如果不定清楚,后面所有算法调优都是在沙滩上盖楼。
我在做这类项目时,会先建一个“缺陷分级表”,把每个检测项分成致命缺陷(必须拦截)、严重缺陷(报警待人工复判)和轻微缺陷(记录但放行)。这个表看起来简单,但它是整个视觉系统逻辑的基石,也直接决定了后面代码里ROI区域划分的粒度和分类器的输出设计。
1.2 为什么选Matlab做算法原型而非直接上C++
工业现场最终部署大概率是C++配合Halcon或OpenCV,但我强烈建议在项目启动阶段用Matlab先跑通算法。原因有三点:
第一,Matlab的Image Processing Toolbox和Computer Vision Toolbox里,像imfindcircles、detectSURFFeatures、fitgeotrans这些函数,封装度极高,十几行代码就能验证一个思路的可行性。如果一上来就用C++写底层,光图像校正和特征提取就得耗掉两三周,而用Matlab可能一个下午就能出初步结果。
第二,Matlab的App Designer和Live Script很适合做算法参数的交互式调试。比如焊点检测的灰度阈值,用一个Slider控件拖一拖,立刻能看到二值化效果的变化。这种直观反馈对参数敏感性分析特别有价值,也能帮你在项目评审时快速向非技术背景的同事展示检测逻辑。
第三,Matlab对科研和算法创新的支持更友好。如果你的项目偏研究性质,比如要尝试深度学习做缺陷分类,Matlab的Deep Learning Toolbox里可以直接导入ONNX模型,甚至用Experiment Manager做批量对比实验,这在纯C++环境下折腾成本很高。
当然,Matlab的短板也明显:部署时需要运行时环境,实时性受解释型语言限制。所以我的建议是,Matlab做算法验证和参数标定,确定最优方案后,再翻译成C++或者生成C代码部署到工控机。这个流程我在多个项目里验证过,能省掉大量返工时间。
1.3 系统架构的顶层设计视角
一致性检测系统从物理架构上分四个模块:图像采集模块、光源控制模块、算法处理模块、结果通信模块。很多初学者把精力全放在算法上,但项目实际出问题最多的往往是前两个模块。
图像采集模块的关键是相机、镜头和采集卡的匹配。这里有一个核心计算:视野范围(FOV)与分辨率的关系。假设你要检测一块200mm×150mm的板卡,最小的缺陷是0.3mm的元件引脚桥连,那么按工业经验,至少要让缺陷区域占据3×3像素以上才能被稳定识别。这样算下来,需要的分辨率就是:200mm / (0.3mm/3) ≈ 2000像素,150mm / (0.1mm) ≈ 4500像素,但实际单相机很难达到这个指标,所以常见的做法是分区拍摄,把板卡分成几个FOV区域,每个区域拍一张高清图。
光源控制模块涉及的是照明方案。PCB检测最常用的是环形低角度光源加同轴光组合,低角度光用来突出焊点和元件轮廓,同轴光用来压制元件本体的反光干扰。光源控制器还要通过IO触发和相机硬同步,确保每次拍照时光照条件一致,这是“一致性检测”这个概念的物理基础——如果两次拍照的光照都不同,那算法再准也白搭。
2. 相机、镜头与光源的选型:从参数到现场经验
2.1 分辨率、靶面尺寸与镜头焦距的联动计算
选相机不是像素越高越好,而是要看“单位像素对应的物理尺寸”是否满足检测精度。这里有一个从业者都该刻在脑子里的概念:像素当量(Pixel Size in Object Space),即每个像素代表的实际物理长度。
计算公式是:像素当量 = FOV宽度(mm) / 相机水平分辨率(pixel)。
举个例子,如果FOV是60mm宽,相机是500万像素(2448×2048),那么水平方向的像素当量就是60/2448 ≈ 0.0245mm/pixel,也就是说一个0.3mm的引脚缺陷在图像里约占12像素,完全够检测了。但如果采集卡或传输带宽限制导致只能跑200万像素,像素当量变成0.05mm/pixel,同样的缺陷只占6像素,算法就得靠边缘拟合和亚像素处理来补,难度和误判率都会明显上升。
镜头焦距的选取则根据工作距离来定:焦距 f = 工作距离(D) × 靶面高度(H) / FOV高度(V)。假设靶面高度是3.6mm(1/2.7英寸相机),工作距离定在200mm,FOV高度要做60mm,那么代入公式:f = 200×3.6/60 = 12mm。所以在常见VisionChina等品牌镜头里,选12mm或16mm定焦就能满足需求。定焦比变焦靠谱,因为变焦镜头在多次调节后容易产生微小的光轴偏移,给“一致性”埋雷。
2.2 光源角度和光谱的讲究
PCB上的元件五花八门,有镜面的IC表面、粗糙的电阻端头、球形的电容焊点,它们对光的反射特性完全不同。所以光源设计不能一招鲜。
我常用的光源策略分三层:
- 同轴光负责IC引脚和丝印区域,它发出的光垂直照射、垂直反射,能清晰呈现平面纹理。
- 低角度环光负责BGA焊点和QFP引脚,低角度入射光会让焊点的曲面产生明暗梯度,焊点饱满与否一览无遗。
- 背光源用在板卡外围轮廓检测上,用来提取板卡边缘和定位基准点。
光源的颜色也讲究。绿色光(520nm左右)是PCB检测的黄金波长,因为绿光在绿色阻焊层上的反射对比度最好,而且能有效抑制环境光的干扰。如果在灯光下加装偏振片,还能进一步消除金属表面的镜面眩光。我在实验室对比过同一块板子在白光和绿光下的检测效果,焊点边缘的清晰度能提升20%以上。
2.3 硬件触发的同步与抖动控制
工业视觉检测最怕的一件事是“图像糊了”。很多糊图不是运动速度过快,而是触发时序不对。相机采集和光源闪光必须严格同步:光源控制器要先收到触发信号、稳定输出后再曝光,曝光完成后再传输图像。这个时间差通常在几十微秒级别,但一旦错位,板子移动过程中就会产生拖影。
在Matlab里做硬件同步调试时,我一般通过videoinput的TriggerRepeat属性设置连续触发模式,再配合manual触发源,确保每帧图像都是在光源稳定后采集的。同时要把ROIPosition设置成只采集板卡所在区域,既减小了数据传输负担,也避免了对焦平面外的无效信息干扰。
2.4 校准与标定的工程细节
硬件装好之后,一定要做两项标定:光学畸变标定和像素当量标定。我见过太多团队跳过这一步直接跑检测算法,结果板卡边缘的定位误差大到2~3个像素,稳定性极差。
畸变标定用Matlab自带的cameraCalibrator就能做,打印一张棋盘格标定板,从不同角度拍20张左右,自动算出内参和畸变系数。像素当量标定更简单,拿一把已知精度的游标卡尺放在FOV里拍一张图,算出像素数和实际尺寸的比值就行。但记住,每次重新调整相机高度、焦距或光圈之后,都要重新做一次标定。这个动作应该写进产线的点检表里,不能靠自觉。
3. 图像预处理与配准:一致性检测的“地基工程”
3.1 光照不均的校正策略
即使有光源系统,PCB板面也难免存在中心亮、边缘暗的情况,这就是光照不均。直接拿这种图做差分,边缘区域会产生大量伪差异,严重影响检测准确率。
处理光照不均,我最常用的套路是形态学背景估计。用imopen和imclose配合一个尺寸大于最大特征的结构元素(比如50×50的圆盘),提取出图像的背景亮度分布,然后用原图减去背景图,就能拉平光照。这个方法比高斯拉普拉斯更稳,因为它对随机噪声不敏感。
操作示例:
% 读取图像 img = imread('pcb_sample.bmp'); imgGray = rgb2gray(img); % 背景估计与补偿 se = strel('disk', 50); bg = imopen(imgGray, se); bg = imclose(bg, se); imgFlat = imsubtract(imgGray, bg); imgFlat = imadjust(imgFlat);用imadjust把灰度范围拉伸到0~255,能够显著提高焊点和引脚的对比度。这一步做完,后面无论是差分还是特征匹配,都会轻松不少。
3.2 图像配准:解决“板子放歪了”的老大难问题
再稳定的夹具也不敢保证每次板卡摆放位置分毫不差,所以一致性检测前必须做图像配准,把当前图像变换到模板图像的位置坐标系下。
配准的流程是:先提取特征点,再估计几何变换模型,最后做图像变换。Matlab里最顺手的是estimateGeometricTransform2D,配合SURF或ORB特征点。对于PCB这种包含大量直线和角点的图像,我倾向于先用detectFASTFeatures找角点,再用extractFeatures算描述子,最后用matchFeatures做特征匹配。相比之下,SURF对于大尺寸图像会稍微慢些,FAST在这个场景下速度与精度更平衡。
变换模型的选择上,如果板卡只是平移和轻微旋转,用affine就够了;如果相机角度有偏差或板卡有透视变形,需要用到projective。注意,变换模型用得过猛(比如projective用在只需affine的场景),会把微小的正常变形放大,产生虚假的检测差异。
配准之后的图像,需要做像素级对齐。有时候imwarp之后的图像会在边缘产生一些插值伪影,所以我会建议在配准后保留一个安全边距,ROI都不要贴着图像边界。
3.3 模板的建立与更新机制
一致性检测绕不开“模板”。模板图的建立不能简单拍一张好板子完事,而是应该从多个合格板卡里综合生成。我通常的做法是采集20~30片确认无缺陷的板卡,做配准后,对每个像素取灰度中值或均值,生成一张标准模板图。如果是深度学习方案,模板还可以作为训练集的基准,配合数据增强生成更多样本。
模板也需要“保养”。当产线换了元件批次,元件颜色和封装可能有细微差异,继续用旧模板会误报率飙升。这时需要重新采集合格样品更新模板,但更新前必须经过工艺和品质部门确认——“新板子确实没问题”才能当模板,否则会把新缺陷学进去。
4. 核心算法实现:从差分检测到深度学习的进阶之路
4.1 灰度差分与阈值分割的界限在哪
模板配准做完之后,最直接的检测手段是灰度差分。把待检图和模板图逐像素相减,得到差分图,再通过阈值二值化提取异常区域。这里的关键是阈值的选取,我习惯用自适应阈值而非固定阈值。
自适应阈值的经典实现是Otsu方法(graythresh),但Otsu对缺陷面积占比很敏感。如果缺陷区域很小(比如只有几百像素),Otsu的阈值会偏向背景,分割不出来。更可靠的方案是基于局部统计的阈值:对差分图做滑窗统计,每个窗口内部计算均值和标准差,如果某点的偏离超过k倍标准差(k取3到5),就认为是异常点。
示例代码:
delta = imabsdiff(imgRegistered, templateImg); % 局部自适应阈值分割 se = strel('disk', 15); localMean = imfilter(delta, fspecial('average', 30), 'replicate'); localStd = stdfilt(delta, ones(15)); mask = (delta - localMean) > 4 * localStd;用stdfilt算出局部标准差,再结合均值做判定,能极大减少噪声导致的误报。实测下来,这个策略比全局阈值在光照波动场景下的鲁棒性提升了至少30%。
4.2 形态学处理与连通域分析:把“问题区域”拎出来
二值化之后,差分图里往往有大量细碎噪声点,需要用形态学开运算去掉。开运算是先腐蚀后膨胀,作用是把小于结构元素尺寸的孤立点清掉。但结构元素尺寸必须根据最小目标缺陷来定,如果缺陷最小是5×5像素,开运算的结构元素不能大于4×4,否则真实缺陷也会被吞掉。
清理完噪声,用bwlabel或bwconncomp做连通域标记,再通过regionprops提取每个连通域的面积、周长、偏心率、方向角等特征。通过这些特征就能过滤掉一些“看起来像缺陷但不是”的区域,比如一个反光点可能面积很小,一个杂质可能偏心率很大,都能被规则过滤掉。
我做了一个简单的过滤逻辑表:
| 特征 | 判定条件 | 说明 |
|---|---|---|
| 面积 | 小于80像素则忽略 | 按像素当量换算成物理尺寸 |
| 周长 | 与面积的比值异常则忽略 | 识别细长划痕与真实桥连 |
| 位置 | 在ROI外则忽略 | 防止板边阴影干扰 |
| 灰度均值 | 接近背景灰度则忽略 | 排除轻微光照差异 |
这一步相当于给算法设定“怀疑门槛”,宁可在后续复判环节多花一点人力,也不要在算法阶段就漏掉真实缺陷。
4.3 特征匹配与分类器:一致性检测的关键进阶
如果板卡上有BGA、QFN这类引脚密集器件,纯灰度差分是不够的,因为焊点的三维形状变化在二维图像里表现得非常微妙。这时候就需要提取局部特征,比如焊点的边缘梯度方向直方图、灰度共生矩阵等。
我在实验里用extractLBPFeatures提取局部二值模式特征,然后训练一个SVM分类器,将每个焊点区域分类为“正常/异常”。在300片板卡、大概3万个焊点的数据集上,SVM的准确率能做到98%左右。如果数据量更大,换成Matlab的fitcecoc多分类器或者直接上深度学习,效果还能更好。
但特征工程有个铁律:特征的选择必须对应物理缺陷模式。比如检测反件,需要重点关注方向性特征;检测虚焊,需要重点关注焊点边缘的阴影梯度;检测错件,需要重点关注丝印区域的字符识别结果。一把抓所有特征,训练出来的模型往往在换产线后迅速失效。
4.4 深度学习辅助:数据增强与迁移学习实战
近几年,基于深度学习的视觉检测已经是主流方向之一。Matlab的Deep Learning Toolbox里,trainNetwork配合imageDatastore就能快速搭建一个分类网络。但对于PCB缺陷检测来说,最大的瓶颈不是网络结构,而是数据量。工业现场真实缺陷样本往往很少,严重的缺陷甚至只有个位数。
应对策略是数据增强和迁移学习的组合。数据增强包括随机旋转、缩放、加噪、弹性形变等,在Matlab里用imageDataAugmenter配置一次,训练时会自动在线增强,把有限的数据“发酵”出更多变体。迁移学习则用googlenet、resnet18这类预训练模型,把最后一层全连接层换成自己的分类层。这样做的好处很明显:即便只有每类100张图,也能训出一个基本可用的分类器,训练时间还能控制在几分钟到十几分钟。
另外一个工程细节是,深度学习的输入图像尺寸,不要盲目统一到224×224,要根据ROI的实际尺寸来定。例如焊点区域原尺寸是32×32,强行压缩放大到224×224反而引入插值噪声,不如把网络第一层输入尺寸调整成64×64或128×128,用'InputSize'参数控制。
5. 实操过程记录:从Matlab代码到可复现的检测Demo
5.1 完整代码流程与参数设置清单
下面是一段我在实际项目中调试过的核心流程,按照“采集→配准→差分→形态学→连通域→判定”的顺序写,附带关键参数说明。
% 1. 采集当前板卡图像 cam = videoinput('winvideo', 1, 'RGB24'); src = getselectedsource(cam); src.ExposureMode = 'manual'; src.Exposure = -6; % 根据现场光照调整,单位与相机驱动相关 triggerconfig(cam, 'manual'); start(cam); trigger(cam); % 硬件触发或手动触发 imgCurrent = getsnapshot(cam); stop(cam); % 2. 图像预处理:直方图均衡化增强局部对比度 imgCurrent = rgb2gray(imgCurrent); imgCurrent = adapthisteq(imgCurrent, 'NumTiles', [8 8], 'ClipLimit', 0.02); % 3. 模板图像加载与配准 % 注意:模板需要预处理流程完全一致,否则配准会失真 load('pcbTemplate.mat', 'templateImg', 'tformRef'); imgRegistered = imwarp(imgCurrent, tformRef, 'OutputView', imref2d(size(templateImg))); % 4. 差分与自适应阈值 diffImg = imabsdiff(imgRegistered, templateImg); se = strel('disk', 3); diffImg = imopen(diffImg, se); % 先开运算去除细碎噪声 localStd = stdfilt(diffImg, ones(11)); threshMask = diffImg > (4 * localStd + 5); % 5为固定偏置,平衡敏感性 % 5. 连通域分析 cc = bwconncomp(threshMask); stats = regionprops(cc, 'Area', 'BoundingBox', 'Centroid'); defectBoxes = []; for k = 1:length(stats) if stats(k).Area > 80 && stats(k).Area < 50000 defectBoxes = [defectBoxes; stats(k).BoundingBox]; end end % 6. 结果可视化与标注 imgMarked = insertShape(imgCurrent, 'Rectangle', defectBoxes, 'LineWidth', 2, 'Color', 'red'); imshow(imgMarked);这套代码在Matlab R2022a及以上版本跑过很多次,算是很稳定的基线流程。如果你的板卡对比度特别低,可以把adapthisteq的ClipLimit调大一点;如果噪声严重,stdfilt的窗口可以缩到9×9,但窗口太小时对轻微缺陷的响应会变弱,需要在敏感性和稳定性之间做个取舍。
5.2 参数标定的工程化方法
上面的代码里,有两个参数最让人头疼:局部标准差的乘数系数(示例代码中是4)和面积阈值(示例代码中是80)。这里面有讲究,不能拍脑袋定。
我的做法是先用20张正常板卡跑一遍算法,收集这些参数在正常情况下的分布范围。比如乘数系数设定为4时,正常板卡的异常像素数在500~2000之间波动,那么把判定阈值设在3000左右就能保证不误报。再用20张故障板卡(含各类已知缺陷)跑一遍,确认这个阈值能把缺陷都框出来。如果故障板卡有遗漏,就逐步降低乘数系数或增加面积下限,直到达到漏检率0%的临界点,再往回留20%的裕量。
标定完之后,把这些参数固化到一个配置文件中,包括params.pc = 4; params.minArea = 80; params.stdfiltWin = 11;。以后换线体或换产品型号时,直接加载一套新的配方参数,而不是改代码,这才是工业软件该有的姿态。
5.3 部署与通信:把检测结果送到PLC或MES
算法跑通之后,要接上产线的“神经末梢”。现场最常见的需求是,检测完成之后把OK/NG信号发给PLC,让机械手把NG板子剔除,同时把缺陷图片和统计信息上传到MES系统。
Matlab里做TCP/IP通信非常方便。用tcpclient创建客户端,与上位机或者PLC网关建立Socket连接,然后把检测结果打包成JSON或自定义协议发送。下面是一段简化的示例:
% 建立TCP连接,IP和端口按现场网络规划配置 t = tcpclient('192.168.1.100', 5000); % 结果结构体 result = struct('boardId', boardId, 'result', 'NG', 'defectCount', length(defectBoxes)); % 编码为JSON后发送 import matlab.lang.makeValidName s = jsonencode(result); write(t, uint8(s));这里要注意的是,Socket通信是异步的,现场要求实时性高的话,必须做线程缓冲和重发机制。另外,检测结果的保存路径要按日期和线体分类存放,方便后续质量追溯。我在MES对接上踩过一个大坑:图片命名用了板卡的流水号,但流水号的位数在不同型号板卡间不一致,导致数据表关联时类型不匹配,后来统一改成16位字符串+时间戳的格式才解决。
6. 常见问题与排查技巧实录
6.1 同一缺陷,两次检测结果不一样
这类问题90%出在光照或者触发上。先把相机固定住,用软件连续采集20帧图像,检查每帧图像的灰度均值和方差。如果帧间灰度波动超过2%,优先检查光源控制器是不是有频闪、光源是不是老化、相机是否处于自动增益模式。一定要把相机的自动增益和自动白平衡关掉,全部改为手动设置,并且把曝光时间锁定。工业检测最忌讳“用自动模式测一致性”,那是自欺欺人。
另外一个隐蔽的原因是温度漂移。相机长时间运行后传感器会发热,暗电流增加会导致图像整体变亮。所以现场环境允许的话,最好让相机开机预热15分钟后再开始正式检测,或者在算法里加一个灰度偏移动态校正。
6.2 误报率居高不下,调阈值也没用
如果你的算法把好板子频繁判成NG,先检查图像配准是不是有问题。很多时候板卡稍微歪一点,配准矩阵算得不够精细,焊盘边缘就会出现亚像素级别的错位,在差分图里表现为一条细线,面积也不大不小,特别容易被误判为桥连。解决办法是配准前先做角点检测的亚像素精确定位,使用cornerPoints的subPixelLocation,把特征点定位精度从1像素提升到0.1像素级别。
还有一种情况是板卡表面有助焊剂残留或轻微手印,灰度差异真实存在,但不是致命缺陷。这时候需要把ROI收紧,只检测焊盘和引脚区域,避开大片铜皮和丝印区,或者在分类阶段加一个“疑似缺陷等级”的判断,让这类轻微异常走人工复判而不是直接NG。
6.3 算法在实验室完美,到了现场就失灵
这是工业项目最常见也最打击人的问题。实验室环境干净、光照恒定、板卡少,现场环境灰尘大、震动大、环境光杂散。所以我在实验室阶段就会“故意制造困难”——把光源角度微调、加入日光灯干扰、模拟板卡微小的位置偏移,提前验证算法的鲁棒性。
如果到了现场才发现算法扛不住,紧急处理方案是把检测ROI缩小,只保留下与关键质量相关的区域,减少干扰输入。但这只是临时手段,根本解法还是在方案设计阶段就引入多光源、遮光罩,并且做充分的工程裕量设计。
6.4 关于处理速度:Matlab太慢怎么办
Matlab在处理高分辨率图像时,确实比C++慢不少。如果一张图的算法耗时超过500ms,产线节拍可能就顶不住了。第一步优化是用mex编译关键函数。Matlab的codegen工具能直接生成C代码,我试过把连通域分析部分单独提出来mex化,整体耗时从800ms降到300ms左右。第二步是降低输入图像分辨率,在一些连续检查项里,用1/2或1/4分辨率做初筛,只有初筛有异常的ROI才做全分辨率精查,这种“由粗到精”的级联策略能节省大量时间。第三步是在软件架构上用一个独立线程做算法处理,同时另一个线程做图像采集,两相重叠能让产线在视觉处理周期内不产生瓶颈。
7. 从研究到落地:一致性检测后续还能怎么扩展
项目做到能稳定跑完500片板卡、误报率控制在0.5%以内,其实已经迈过了工业应用的门槛。但这个方向还可以继续深挖下去,我个人最看好两个扩展方向。
第一个方向是多视角融合检测。单相机只能看板卡的一个面,但很多缺陷(比如通孔内壁的铜脱落、连接器引脚的开焊)其实发生在侧面或内部。通过多个相机从不同角度采集,再在算法层做空间融合定位,能够覆盖更多的检测盲区。Matlab在这个方向上的多视角几何工具很成熟,比如estimateFundamentalMatrix、triangulate这些函数都能直接调用。
第二个方向是数字孪生与虚拟调试。在产线还处于设计阶段时,用Matlab仿真生成“虚拟缺陷样本”,比如给正常板卡图像合成一模一样的焊点偏移、桥连效果,用这些仿真样本来预训练算法,到了真机联调阶段就能显著缩短爬坡时间。这一套思路和无人驾驶领域的仿真测试很像,目前电子制造行业里普及度还不高,先跑通的人会有很大的先发优势。
回到我开始说的那句话,一致性检测这个领域,真正的壁垒不在算法,而在工程细节。从光路设计、标定流程到参数配置管理,每一个环节都有可能让精度断崖式下跌。我踩过的那些坑——自动增益没关、模板用了有瑕疵的板子、畸变标定偷懒没做——说出来都是一个比一个简单的失误,但在项目现场都曾让我加班到怀疑人生。如果你正在做类似的PCB检测项目,希望这篇文章里的数据和流程能帮你少走几段弯路。至少下次遇到“同一块板子两次检测结果不同”的问题时,你已经知道该从哪查起了。