Opencv图像识别从零到精通|Opencv图像识别从零到精通(18)-------击中击不中
在我们学习了膨胀腐蚀和基于膨胀腐蚀的变化之后,我比较喜欢的一个是击中击不中,因为喜欢所以就要单独列出来,心里总是觉得他可以有很多的用处,以后模版匹配,特征检测都会用,更深入的是,他会加深对膨胀腐蚀的理解,是一个很好的例子。
下面先看一个算法步骤和原理:
Hit-miss算法步骤:
击中击不中变换是形态学中用来检测特定形状所处位置的一个基本工具。它的原理就是使用腐蚀;如果要在一幅图像A上找到B形状的目标,我们要做的是:
- 首先,建立一个比B大的模板W;使用此模板对图像A进行腐蚀,得到图像假设为Process1;
- 其次,用B减去W,从而得到V模板(W-B);使用V模板对图像A的补集进行腐蚀,得到图像假设为Process2;
- 然后,Process1与Process2取交集;得到的结果就是B的位置。这里的位置可能不是B的中心位置,要视W-B时对齐的位置而异;
其实很简单,两次腐蚀,然后交集,结果就出来了。
Hit-miss原理:
基于腐蚀运算的一个特性:腐蚀的过程相当于对可以填入结构元素的位置作标记的过程。
腐蚀中,虽然标记点取决于原点在结构元素中的相对位置,但输出图像的形状与此无关,改变原点的位置,只会导致输出结果发生平移。
既然腐蚀的过程相当于对可以填入结构元素的位置作标记的过程,可以利用腐蚀来确定目标的位置。
进行目标检测,既要检测到目标的内部,也要检测到外部,即在一次运算中可以同时捕获内外标记。
由于以上两点,采用两个结构基元H、M,作为一个结构元素对B=(H,M),一个探测目标内部,一个探测目标外部。当且仅当H平移到某一点可填入X的内部,M平移到该点可填入X的外部时,该点才在击中击不中变换的输出中。
opencv应用
Mat src;
src=https://www.it610.com/article/imread("2312.png",0);
Mat input_image = src;
Mat Kernel_S1 = imread("2311.png");
cvtColor(Kernel_S1, Kernel_S1, CV_RGB2GRAY);
int threhold = 180;
threshold(input_image, input_image, threhold, 255, CV_THRESH_BINARY);
threshold(Kernel_S1, Kernel_S1, threhold, 255, CV_THRESH_BINARY);
imshow("二值化图像", input_image);
Mat BigBlankimage = Mat::ones(input_image.size(), input_image.type());
input_image = BigBlankimage*255-input_image;
imshow("反置图像", input_image);
Mat Blankimage = Mat::ones(Kernel_S1.rows, Kernel_S1.cols, CV_8UC1);
Mat Kernel_S2 = Blankimage * 255 - Kernel_S1;
imshow("核1", Kernel_S1);
imshow("核2", Kernel_S2);
Mat hit_result, hit_result1, hit_result2;
erode(input_image, hit_result1, Kernel_S1, Point(-1,-1), 1, BORDER_DEFAULT, 0);
imshow("hit_result1", hit_result1);
erode(input_image, hit_result2, Kernel_S2, Point(-1,-1), 1, BORDER_DEFAULT, 0);
imshow("hit_result2", hit_result2);
hit_result = hit_result1 & hit_result2;
imshow("击中击不中", hit_result);
matlab应用之函数使用与自定义实现 只要定义好s1 s2 调用bwhitmiss
Ihm = bwhitmiss(I, S1, S2);
% I为输入图像
% S1、S2为结构元素
根据冈萨雷斯的书的说明,如下图,然后用matlab编写代码,最后得到图像
文章图片
clear all;
I = zeros(120,180);
I(11:80,16:75) = 1;
I(56:105,86:135) = 1;
I(26:55,141:170) = 1;
figure,imshow(I);
se = zeros(58,58);
se(5:54,5:54) = 1;
figure,imshow(se);
%击中击不中变换
Ie1 = imerode(I,se);
figure,imshow(Ie1);
Ic = 1 - I;
figure,imshow(Ic);
S2 = 1 - se;
figure;
imshow(S2);
Ie2 = imerode(Ic,S2);
figure,imshow(Ie2);
Ihm = Ie1 & Ie2;
figure,imshow(Ihm);
这里我们看一下结果
【Opencv图像识别从零到精通|Opencv图像识别从零到精通(18)-------击中击不中】
文章图片
图像识别算法交流 QQ群:145076161,欢迎图像识别与图像算法,共同学习与交流
推荐阅读
- opencv|opencv C++模板匹配的简单实现
- Java|Java OpenCV图像处理之SIFT角点检测详解
- 人脸识别|【人脸识别系列】| 实现自动化妆
- Spring|Spring 框架之 AOP 原理剖析已经出炉!!!预定的童鞋可以识别下发二维码去看了
- 识别人才
- 从前沿科技到现实应用,人脸识别智能门禁加速走进智慧社区
- ImageLoaders 加载图像
- JAVA图像处理系列(四)——噪声
- 《不要用爱控制我》
- OpenCV|OpenCV-Python实战(18)——深度学习简介与入门示例