算法效果展示
1 要定位的模板1
找到的匹配
在有污损情况下找到的匹配
2要定位的模板2
找到的匹配
一. 理论部分
模板匹配的算法包括基于灰度的匹配,基于特征的匹配,基于组件的匹配,基于相关性的匹配以及局部变形匹配。基于灰度的匹配一般应用在没有缩放和旋转,颜色变化不大的场合。基于特征的匹配一般应用在具有缩放和旋转,颜色变化较大的场合。在模板各个组件有相对位移的情况下,使用基于组件的匹配算法。在图像模糊,目标定位不依赖于边缘的情况下一般使用基于相关性的匹配。目标有局部变形的情况使用局部变形匹配算法。基于特征的匹配算法通常使用线特征即轮廓特征,也有使用点特征(ICP算法和RANSAC算法)和面特征(基于区域,基于纹理等)的方法。本文主要介绍基于轮廓特征的模板匹配。
基于轮廓的模板匹配其相似度分布比基于灰度的模板匹配更加有区分度,因而可以进行较高精度的定位。同时,由于只对轮廓进行处理,因而提高了处理速度,因此在处理带有旋转和缩放的情况时具有优势。另外,基于轮廓特征的模板可以不从现场获取,而从CAD数据生成。
二.实验部分:
2.1实验一:边缘模板创建
(Canny算法+非极大值已知+滞后阈值)
在opencv中有函数findcontour可以找到二值图中的边缘,但需要人为控制二值化参数并观察结果,对于灰度区域较多的模板,并不能找到所有边缘,因此使用Canny边缘检测方法,然后进行非极大值抑制和滞后阈值处理得到的边缘。
原图:
找到的边缘点
代码
C++
int myfindcontour(Mat templateArr, double maxContrast, double minContrast){
Mat src = templateArr.clone(); //变量定义 Size Ssize; Ssize.width = src.cols; Ssize.height = src.rows; modelHeight = src.rows; modelWidth = src.cols; noOfCordinates = 0; cordinates = new Point[modelWidth *modelHeight]; edgeMagnitude = new double[modelWidth *modelHeight]; edgeDerivativeX = new double[modelWidth *modelHeight]; edgeDerivativeY = new double[modelWidth *modelHeight]; //使用Sobel算子计算梯度 GaussianBlur(src, src, Size(5,5), 1); Mat gx, gy; gx = Mat(Ssize.height, Ssize.width, CV_16SC1); gy = Mat(Ssize.height, Ssize.width, CV_16SC1); Sobel(src, gx, CV_16S, 1, 0, 3); Sobel(src, gy, CV_16S, 0, 1, 3); Mat nmsEd