表面缺陷检测算法:PatchCore 与 PaDiM 等方法
表面缺陷检测算法:PatchCore 与 PaDiM 详解
1. 什么是表面缺陷检测
表面缺陷检测是工业视觉质检的核心任务,目标是从正常样本中识别出划痕、凹坑、污渍、裂纹等异常。与通用目标检测不同,缺陷通常形态多变、尺度不一且缺乏大量标注数据,因此无监督与半监督方法成为主流。
基于深度学习的缺陷检测方法大致分为:
- 基于重构:如自编码器、GAN,通过重建误差定位异常,但容易模糊缺陷边界。
- 基于嵌入:利用预训练CNN提取图像块特征,在特征空间中衡量测试样本与正常样本分布的偏离,代表方法为SPADE、PaDiM、PatchCore。
- 基于知识蒸馏:如STPM,让学生网络模仿教师网络对正常样本的响应,通过差异图发现异常。
- 基于合成:如CutPaste、NSA,通过人工生成异常样本训练判别模型。
其中,PatchCore 与 PaDiM 凭借简单、高效且无需训练的在线阶段,成为工业界热门选择。本教程将重点解析这两种方法的原理与实现要点。
2. 核心思想:记忆正常特征,度量异常偏离
基于嵌入的方法遵循“正常特征库 + 距离度量”范式:
- 使用在ImageNet上预训练的CNN(如ResNet、WideResNet)作为固定特征提取器。
- 将每张正常图像切分为多个图像块(patch),逐块提取特征向量(通常使用多层级融合)。
- 收集所有正常训练样本的patch特征,构建正常特征库。
- 测试时,对测试图像的每个patch提取相同特征,在特征库中检索最近邻或计算到正常分布的距离,得到异常分数。
- 对异常分数图进行后处理(高斯模糊、阈值分割)生成缺陷检出结果。
PaDiM 与 PatchCore 的区别在于如何构建正常特征库以及如何度量异常。
3. PaDiM:为每个位置建立多元高斯分布
3.1 思路
PaDiM 假设同一空间位置的图像块特征服从多元高斯分布。训练时,统计所有正常样本同一位置 patch 的特征均值与协方差矩阵;测试时,计算马氏距离作为异常分数。
3.2 特征提取细节
- 使用预训练 CNN(如 ResNet18、WideResNet50),移除最后分类层,保留3个中间层输出(如 layer1、layer2、layer3)。
- 对每层特征图进行双线性插值,统一到最大特征图尺寸,在通道维度拼接,得到每个 patch 的多尺度特征向量。
- 特征向量维度可能较高(例如 ResNet18 三层通道数 64+128+256=448),协方差矩阵计算开销大。PaDiM 通过随机降维(将特征随机分配到多个子空间)或 PCA 简化协方差矩阵。
3.3 异常分数计算
对位置 (i, j) 的特征向量 x,其异常分数为:
$$ s_{ij} = \sqrt{ (\mathbf{x} - \boldsymbol{\mu}{ij})^T \mathbf{\Sigma}^{-1}{ij} (\mathbf{x} - \boldsymbol{\mu}_{ij}) } $$
其中,均值 μ_{ij} 和协方差 Σ_{ij} 由训练集对应位置的所有特征估计得到。最终得到一个宽高与最大特征图相同的异常分数图。
3.4 优缺点
优点:
- 推理速度快,仅需一次前向传播和查表计算。
- 对位置的微小偏移具有一定鲁棒性(马氏距离考虑了特征分布的方差)。
- 无需额外存储特征库,仅存储每个位置的统计量(均值、协方差矩阵)。
缺点:
- 严格要求图像对齐,空间偏移会使假设失效。
- 当训练样本较小或特征维度高时,协方差矩阵估计不稳定,可能产生虚假高异常分数。
- 整图仍需要存储大量位置(如 64×64 个位置,每个都有协方差矩阵),内存占用有时并不低。
4. PatchCore:记忆核心正常特征集
4.1 思路
PatchCore 放弃高斯假设,直接使用特征记忆库(memory bank)存储正常样本的典型 patch 特征。它通过贪婪核心集采样来压缩特征库容量,保留最具代表性的邻域样本,测试时对每个测试 patch 进行最近邻搜索,以距离作为异常分数。
4.2 特征提取
- 同样基于预训练网络,但通常只使用中间某一层(如 ResNet 的 layer2、layer3 输出),经验表明中级特征对纹理边缘敏感,适合缺陷。
- 对整张特征图,所有空间位置(即所有 patch)的特征都视为正常特征候选,扁平化后得到一个庞大的特征集合
M(可能包含数千万个特征向量)。这称为“名义特征池”。
4.3 特征库构建:贪婪核心集采样
直接存储全量特征库内存巨大且检索慢。PatchCore 使用**核心集(coreset)**技术减少特征数目:
- 目标:找一个小集合
S ⊂ M,使得M中任意点到S中最近点的最大距离最小化(minimax facility location 问题)。 - 采用贪婪近似:初始化
S含一个随机点,不断选取M中到S距离最远的点加入S,直到达到预设比例(如 1%)或数目上限。 - 最终得到特征库
S,大小可压缩两个数量级,仍能较好覆盖正常特征的分布域。
4.4 测试与异常检测
对测试图像每个位置的特征向量 m_test:
- 计算到核心集
S中所有特征的距离,取最小距离(如 L2 距离)作为该位置的异常分数:
$$ s = \min_{\mathbf{s} \in S} | \mathbf{m}_{\text{test}} - \mathbf{s} |_2 $$ - 为了增强局部一致性,常对分数图进行高斯平滑。
- 可进一步对整图所有 patch 分数求最大值或设定阈值判断图像级异常。
部分实现还会结合邻域匹配,即不仅搜索测试 patch 本身,也考虑其周围小邻域特征的匹配,以提升对大范围纹理偏差的敏感度。
4.5 优缺点
优点:
- 不依赖位置对齐,特征库存储的是无位置信息的“纯外观”特征,允许测试图像与训练图像存在一定平移、旋转。
- 直接使用距离度量,避免了高斯假设失效带来的假阳性。
- 核心集大大降低了内存和检索开销,使该方法能部署在边缘设备。
缺点:
- 需要存储特征库(几万到几十万条 1024 维向量),检索时需进行 k-NN,实时性不如 PaDiM 的马氏距离查表。
- 对极端正常样本多样性不足的场景,核心集可能丢失边缘正常模式,造成误检。
- 采样比例与贪婪算法参数需要根据数据集调整。
5. 方法对比与选择建议
| 特性 | PaDiM | PatchCore |
|---|---|---|
| 假设 | 位置相关,高斯分布 | 位置无关,基于邻域距离 |
| 对齐要求 | 严格对齐 | 较宽松,允许少量平移 |
| 推理速度 | 极快(仅需均值/协方差查表) | 中等(需要对核心集进行近邻搜索) |
| 内存占用 | 存储每位置协方差矩阵(可压缩) | 存储核心集特征向量(可控大小) |
| 小样本鲁棒性 | 协方差估计不稳定 | 特征池足够大时鲁棒 |
| 适用场景 | 固定视角、高精度对齐检测 | 位置变化、纹理多样性高的场景 |
选择建议:
- 当待检物定位精确(如水平放置的电子元件)且希望推理极快时,优先考虑 PaDiM。
- 当拍摄角度略有变化、缺陷类型复杂且允许一定延迟时,PatchCore 更灵活。
- 二者可结合:先用 PatchCore 的宽松特征库进行粗筛,再用 PaDiM 进行精确定位。
6. 实现与调优指南
6.1 数据预处理
- 统一图像尺寸(如 256×256),保持长宽比,必要时进行中心裁剪。
- 使用 ImageNet 均值/标准差归一化。
- 扩充正常样本多样性(亮度、对比度、轻微仿射变换)以提高泛化能力,但注意不要破坏正常模式边界。
6.2 骨干网络选择
- 普通 ResNet18/50 足够,WideResNet50 在纹理复杂的场景表现更优。
- 特征层选择:PaDiM 通常用 layer1、layer2、layer3 拼接;PatchCore 建议用 layer2 或 layer3 单一输出(约 1024 维),平衡局部细节与语义。
6.3 降维与采样
- PaDiM 中,将高维特征随机分成 4-8 组分别计算协方差,或使用 PCA 降至 100 维以下,减轻计算和过拟合。
- PatchCore 核心集采样比例建议为训练集总 patch 数的 0.1%~1%,贪婪迭代次数可设为目标核心集大小的 10 倍。
6.4 后处理优化
- 异常分数图使用 σ=4 的高斯滤波平滑,消除破碎噪声。
- 使用 OTSU 或自适应阈值分割缺陷区域,也可根据验证集固定阈值。
- 图像级判断可取分数图的最大值或 Top-10 平均值与阈值比较。
6.5 硬件加速
- PatchCore 的近邻检索可利用 FAISS 库实现近似搜索,在 GPU 上可达毫秒级。
- PaDiM 可以提前将协方差矩阵和均值保存为文件,推理时直接加载并计算马氏距离。
7. 总结
PaDiM 与 PatchCore 代表了基于嵌入的两种经典范式:位置依赖的概率模型与无位置的记忆库距离度量。它们都完美利用了预训练 CNN 的强大表示能力,无需在目标数据集上训练,只涉及少量统计与检索。理解两者的原理与适用边界,能帮助工程师快速搭建可靠的表面缺陷检测系统。
进一步的优化方向包括:使用自监督预训练骨干(如 DINO)提升特征鉴别力;引入异常分数校准技术(如 TTA、温度缩放);以及与合成异常方法结合,在训练阶段利用少量缺陷样本微调特征库等。