形态学处理

形态学图像处理一般应用于二进制图像。

:可以是任何形状和大小,拥有一个单独定义的参考点,称为锚点。多数情况下,核是一个小的,中间有参考点和实心正方形或者圆盘。
核的构造:

getStructuringElement();

第一个参数:表示内核的形状。MORPH_RECT矩形,MORPH_CROSS交叉形,MORPH_ELLIPESE椭圆形。

基本形态学操作

功能:

  1. 消除噪声。
  2. 分割出独立的图像元素,在图像中连接相邻的元素。
  3. 求出图像的梯度。

腐蚀

理解: 低暗部分的扩长。
核心思想: 求局部最小值。核覆盖区域内的像素最小值赋给锚点。

void erode(InputArray src,
		   OutputArray dst,
		   InputArray kernel,
		   Point anchor=Point(-1, -1),
		   int iterations = 1,
		   int borderType = BORDER_CONSTANT,
		   const Scalar& borderValue = morphologyDefaultBorderValue()
);
  • 第一个参数:
  • 第二个参数:
  • 第三个参数:
  • 第四个参数:
  • 第五个参数:
  • 第六个参数:
  • 第七个参数:

膨胀

理解: 高亮部分的扩张
核心思想: 求局部最大值。核覆盖区域内的像素最大值赋给锚点。

void dilate(InputArray src,
			OutputArray dst,
			InputArray kernel,
			Point anchor = Point(-1, -1),
			int iterations = 1,
			int borderType = BORDER_CONSTANT,
			const Scalar& borderValue = morphologyDefaultBorderValue()
			);
  • 第一个参数:
  • 第二个参数:
  • 第三个参数:
  • 第四个参数:
  • 第五个参数:
  • 第六个参数:
  • 第七个参数:

高级形态学操作

开运算

先腐蚀后膨胀
消除小物体,

闭运算

通俗解释:先膨胀后腐蚀。
dst = clese(src,element) = erode(dilate(src, element))
功能:排除小型黑色区域。

形态学梯度

通俗解释:膨胀图和腐蚀图之差。
功能:使二值图像的边缘突出出来。保留物体的边缘轮廓。

顶帽

主要思想:原图像与开运算的结果图之差。
功能:突出比原图轮廓周围更亮的区域。
应用:

黑帽

闭运算的结果图和原图像之差。
功能:突出比原图像轮廓周围区域更暗的区域。
应用:得到完美的轮廓。

在这里插入图片描述

void morphologyEx(InputArray src,
				  OutputArray dst,
				  int op,
				  InputArray kernel,
				  Point anchor = Point(-1, -1),
				  int iterations = 1,
				  int borderTyper = BORDER_CONSTANT,
				  constScalar& borderValue = morphologyDefaultBorderValue()
);
  • 第一个参数:
  • 第二个参数:
  • 第三个参数:形态学运算的类型。决定switch里的选择。
  • 第四个参数:运算内核。
  • 第五个参数:
  • 第六个参数:迭代函数的次数,默认为1。
  • 第七个参数:
  • 第八个参数:

源码详解:

void morphologyEx(InputArray _src,
				  OutputArray _dst,
				  int op,
				  InputArray kernel,
				  Point anchor,
				  int iterations = 1,
				  int borderTyper,
				  constScalar& borderValue );
{	
	//复制Mat数据到临时变量
	Mat src = _src.getMat();
	Mat temp;
	_dst.create(src.size(), src.type());
	Mat dst = _dst.getMat();

	// 一个大的switch,根据不同的标识符获取不同的操作
	switch(op)
	{
		case MORPH_ERODE:
		{
			erode(src, dst, kernel, anchor, iterations, borderType, borderValue);
			break;
		}
		case MORPH_DILATE:
		{
			dilate(src, dst, kernel, anchor, erations, borderType, borderValue);
			break;
		}
		case MORPH_OPEN:
		{
			erode(src, dst, kernel, anchor, erations, borderType, borderValue);
			break;
		}
		case CV_MOP_CLOSE:
		{
			dilate(src, dst, kernel, anchor, erations, borderType, borderValue);
			erode(src, dst, kernel, anchor, erations, borderType, borderValue);
			break;
		}
		
		case CV_MOP_GRADIENT:
		{
			erode(src, dst, kernel, anchor, erations, borderType, borderValue);
			dilate(src, dst, kernel, anchor, erations, borderType, borderValue);
			dst -= temp;
			break;
		}
		case CV_MOP_TOPHAT:
		{
			if(src.data != dst.data)
			{
				temp = dst;
			}
			erode(src, dst, kernel, anchor, erations, borderType, borderValue);
			dilate(src, dst, kernel, anchor, erations, borderType, borderValue);
			dst = src - temp;
			break;
		}
		case CV_MOP_BLACKHAT:
		{
			if(src.data != dst.data)
			{
				temp = dst;
			}
			dilate(src, dst, kernel, anchor, erations, borderType, borderValue);
			erode(src, dst, kernel, anchor, erations, borderType, borderValue);
			dst = temp - src;
			break;
		}
		default:
			CV_Error(CV_StsBadArg, "unknow morphological operation");
	}
}
				  
©️2020 CSDN 皮肤主题: 1024 设计师:上身试试 返回首页