形态学算子根据图像的形状来处理图像。这些操作符将一个或多个结构化元素应用于输入图像以获得输出图像。腐蚀和膨胀是两种基本的形态学操作。这两个操作的组合可以产生高级形态学操作,如开运算、闭运算或顶帽、黑帽等。要了解更多关于这些和其他基本形态学操作的信息,请参阅前面的教程。
Hit-or-Miss操作对于在二值图像中寻找指定模式是很有用的。它能发现那些邻域像素匹配第一个结构元素B1的形状而同时不匹配第二个结构元素B2的形状的像素。从数学上讲,对图像A进行Hit-or-Miss的操作可以表示为:
因此,Hit-or-Miss操作包括三个步骤:
结构元素B1和B2可以组合成一个元素b。让我们看一个例子:
在本例中,我们试图寻找一种模式,其中中心像素属于背景(-1),而中心像素的上下左右相邻的像素属于前景。其他邻域像素可以是任何类型的,我们不关心它们。现在,让我们把这个内核应用到输入图像上:
使用上述结构元素进行Hit-or-Miss操作后得到如下结果:
OpenCV中,使用函数cv::morphologyEx实现Hit-or-Miss操作,指定op参数为MORPH_HITMISS即可,函数在前面的教程中已经详细介绍过,此处不再赘述。
使用实例:
#include
using namespace cv;
int main(int argc, char** argv)
{
// 定义输入图像像素矩阵,0代表背景(黑色),255代表前景(白色)
Mat input_image = (Mat_<uchar>(8, 8) <<
0, 0, 0, 0, 0, 0, 0, 0,
0, 255, 255, 255, 0, 0, 0, 255,
0, 255, 255, 255, 0, 0, 0, 0,
0, 255, 255, 255, 0, 255, 0, 0,
0, 0, 255, 0, 0, 0, 0, 0,
0, 0, 255, 0, 0, 255, 255,0,
0, 255, 0, 255, 0, 0, 255,0,
0, 255, 255, 255, 0, 0, 0, 0);
// 自定义结构元素,0表示无关紧要,1表示匹配的前景元素,0表示匹配的背景元素
Mat kernel = (Mat_<uchar>(3, 3) <<
0, 1, 0,
1, -1, 1,
0, 1, 0);
Mat output_image;
// 调用API执行Hit-or-Miss操作,与其它形态学操作的调用方式类似
morphologyEx(input_image, output_image, MORPH_HITMISS, kernel);
const int rate = 50;
// 将kernel同比扩大50倍后可视化,注意需要调用函数cpnvertTo转换数值类型即图像的深度depth
kernel = (kernel + 1) * 127;
kernel.convertTo(kernel, CV_8U);
// 根据缩放比例调整图像大小
resize(kernel, kernel, Size(), rate, rate, INTER_NEAREST);
imshow("kernel", kernel);
moveWindow("kernel", 0, 0);
// 调整并可视化输入图像
resize(input_image, input_image, Size(), rate, rate, INTER_NEAREST);
imshow("Original", input_image);
moveWindow("Original", 0, 200);
// 调整并可视化输出图像
resize(output_image, output_image, Size(), rate, rate, INTER_NEAREST);
imshow("Hit or Miss", output_image);
moveWindow("Hit or Miss", 500, 200);
waitKey(0);
system("pause");
return EXIT_SUCCESS;
}