OpenCV – 图像二值化处理 腐蚀膨胀 边缘检测 轮廓识别

目录

一:图像二值化

二:膨胀 腐蚀 开闭运算

三:滤波

四:边缘检测

五:物体轮廓线[特征标记]


一:图像二值化

什么是图像二值化

二值化是通过遍历灰度图中点,将图像信息二值化处理,处理过后的图片只有二种色值。

示例如下图所示:

二值化的作用

图像的二值化就是将图像上的像素点的灰度值设置为0或255,这样将使整个图像呈现出明显的黑白效果。在数字图像处理中,二值图像占有非常重要的地位,图像的二值化使图像中数据量大为减少,从而能凸显出目标的轮廓 

二值化的过程   全局阈值 局部阈值

二值化的过程:全局阈值

函数:threshold()

函数参数:

第一个参数,InputArray类型的src,输入数组,填单通道 , 8或32位浮点类型的Mat即可

第二个参数,OutputArray类型的dst,函数调用后的运算结果存在这里,即这个参数用于存放输出结果,且和第一个参数中的Mat变量有一样的尺寸和类型

第三个参数,double类型的thresh,阈值的具体值

第四个参数,double类型的maxval,当第五个参数阈值类型type取 THRESH_BINARY 或THRESH_BINARY_INV阈值类型时的最大值

第五个参数,int类型的type,取阀值的算法

•0: THRESH_BINARY  当前点值大于阈值时,取Maxval,也就是第四个参数,下面再不说明,否则设置为0
•1: THRESH_BINARY_INV 当前点值大于阈值时,设置为0,否则设置为Maxval
•2: THRESH_TRUNC 当前点值大于阈值时,设置为阈值,否则不改变
•3: THRESH_TOZERO 当前点值大于阈值时,不改变,否则设置为0
•4: THRESH_TOZERO_INV  当前点值大于阈值时,设置为0,否则不改变

二值化的过程:局部阀值

什么是局部阀值/自适应阈值

自适应阈值,是根据像素的邻域块的像素值分布来确定该像素位置上的二值化阈值。 

好处

1. 每个像素位置处的二值化阈值不是固定不变的,而是由其周围邻域像素的分布来决定的。

2. 亮度较高的图像区域的二值化阈值通常会较高,而亮度低的图像区域的二值化阈值则会相适应的变小。

3. 不同亮度、对比度、纹理的局部图像区域将会拥有相对应的局部二值化阈值。

函数:adaptiveThreshold()

函数参数:

参数1:InputArray类型的src,输入图像,填单通道,单8位浮点类型Mat即可

参数2:函数运算后的结果存放在这。即为输出图像

参数3:预设满足条件的最大值

参数4:指定自适应阈值算法。可选择ADAPTIVE_THRESH_MEAN_C 或 ADAPTIVE_THRESH_GAUSSIAN_C两种。(具体见下面的解释)。

参数5:指定阈值类型。可选择THRESH_BINARY或者THRESH_BINARY_INV两种。(即二进制阈值或反二进制阈值)。

参数6:表示邻域块大小,用来计算区域阈值,一般选择为3、5、7......等。

参数7:参数C表示与算法有关的参数,它是一个从均值或加权均值提取的常数,可以是负数。(具体见下面的解释)

自适应阈值化计算大概过程是为每一个象素点单独计算的阈值,即每个像素点的阈值都是不同的,就是将该像素点周围B*B区域内的像素加权平均,然后减去一个常数C,从而得到该点的阈值。B由参数6指定,常数C由参数7指定。

ADAPTIVE_THRESH_MEAN_C,为局部邻域块的平均值,该算法是先求出块中的均值,再减去常数C。

ADAPTIVE_THRESH_GAUSSIAN_C,为局部邻域块的高斯加权和。该算法是在区域中(x, y)周围的像素根据高斯函数按照他们离中心点的距离进行加权计算,再减去常数C。

二:膨胀 腐蚀 开闭运算

什么是膨胀 腐蚀

腐蚀和膨胀是针对图片的二值化数据进行操作的主要是针对高亮部分。

膨胀就是使用算法,将图像的边缘扩大些。作用就是将目标的边缘或者是内部的坑填掉。

腐蚀就是使用算法,将图像的边缘腐蚀掉。作用就是将目标的边缘的“毛刺”踢除掉。

腐蚀 膨胀 示例如下图所示:

膨胀过程:

膨胀是求局部最大值的操作,核B与图形卷积,即计算核B覆盖的区域的像素点的最大值,并把这个最大值赋值给参考点指定的像素。这样就会使图像中的高亮区域逐渐增长。

膨胀过程示例如下图所示: 

腐蚀过程:

腐蚀可以理解为B的中心(锚点)沿着A的内边界走了一圈。腐蚀也是对高亮部分而言,A区域之外的部分 < A的高亮像素,所里里面被外面取代 

 腐蚀过程示例如下图所示: 

开运算:先腐蚀再膨胀,用来消除小物体 

开运算常应用于去掉高亮物体背景中白色的噪点,凸显高亮物体 

开运算示例如下图所示:

闭运算:先膨胀再腐蚀,用于排除小型黑洞

闭运算常应用于去掉高亮物体内部的黑色小坑洞,凸显高亮物体 

闭运算示例如下图所示:

三:滤波

滤波处理分为两大类:线性滤波和非线性滤波。

•线性滤波:方框滤波、均值滤波、高斯滤波
•非线性滤波:中值滤波、双边滤波

主要了解高斯滤波和双边滤波

高斯滤波:

高斯滤波用于平滑图像,或者说是图像模糊处理,因此高斯滤波是低通的。其广泛的应用在图像处理的减噪过程中,尤其是被高斯噪声所污染的图像上。

 opencv中GaussianBlur函数实现了高斯滤波效果

函数原型:

void GaussianBlur(InputArray src, OutputArray dst, Size ksize, double sigmaX, double sigmaY=0, int borderType=BORDER_DEFAULT);

参数介绍:

src,输入图像

dst,即目标图像

ksize,高斯内核的大小,必须为正数和奇数

sigmaX,表示高斯核函数在X方向的的标准偏差

sigmaY,表示高斯核函数在Y方向的的标准偏差。若sigmaY为零,就将它设为sigmaX,如果sigmaX和sigmaY都是0,那么就由ksize.width和ksize.height计算出来。

双边滤波

•双边滤波(Bilateral Filter)是非线性滤波中的一种。这是一种结合图像的空间邻近度与像素值相似度的处理办法。在滤波时,该滤波方法同时考虑空间临近信息与颜色相似信息,在滤除噪声、平滑图像的同时,又做到边缘保存。
•双边滤波采用了两个高斯滤波的结合。一个负责计算空间邻近度的权值,也就是常用的高斯滤波器原理。而另一个负责计算像素值相似度的权值。在两个高斯滤波的同时作用下,就是双边滤波。

opencv中bilateralFilter函数实现了高斯滤波效果

函数原型:

bilateralFilter( InputArray src, OutputArray dst, int d,double sigmaColor, double sigmaSpace,int borderType = BORDER_DEFAULT );

参数:

src,输入图像

dst,输出图像

d:滤波邻域直径。如果这个值设为负数,那么这个值由参数sigmaColor计算出。

sigmaColor:滤波的色彩空间参数。这个值越大,代表滤波计算邻域内有更多的色彩权重。

sigmaSpace :滤波的距离空间参数。这个值越大,代表当颜色距离相同时,会有更多的点被影响到。如果参数d>0,则邻域大小由d指定,否则,d是sigmaSpace的一个比例结果。

四:边缘检测

边缘检测的一般步骤

滤波:边缘检测算法主要是基于图像强度的一阶和二阶导数,但是导数对于噪声很敏感,因此需要采用滤波器来改善与噪声有关的边缘检测器的性能

增强:增强边缘的基础是确定图像各点邻域强度的变化值。增强算法可以将灰度点邻域强度值有显著变化的点凸显出来

检测:邻域中有很多的点的梯度值较大,但是在特定的应用中,这些点并不是要找的边缘点,需要取舍

canny边缘检测

canny边缘检测的步骤

1 噪声去除

  由于边缘检测很容易受到噪声影响,所以第一步是使用 5x5 的高斯滤波器去除噪声。

2 计算图像梯度

  对平滑后的图像使用 Sobel 算子计算水平方向和竖直方向的一阶导数(图像梯度)(Gx 和 Gy)

3、非极大值抑制

  在获得梯度的方向和大小之后,应该对整幅图像做一个扫描,去除那些非边界上的点。对每一个像素进行检查,看这个点的梯度是不是周围具有相同梯度方向的点中最大的。

4 滞后阈值

  现在要确定那些边界才是真正的边界。这时我们需要设置两个阈值:minVal 和 maxVal。当图像的灰度梯度高于 maxVal 时被认为是真的边界,那些低于 minVal 的边界会被抛弃。如果介于两者之间的话,就要看这个点是否与某个被确定为真正的边界点相连,如果是就认为它也是边界点,如果不是就抛弃。

滞后阈值

如下图,A 高于阈值 maxVal 所以是真正的边界点,C 虽然低于 maxVal 但高于minVal 并且与 A 相连,所以也被认为是真正的边界点。而 B 就会被抛弃,因为他不仅低于 maxVal 而且不与真正的边界点相连。所以选择合适的 maxVal和 minVal 对于能否得到好的结果非常重要。

CANNY实现

Opencv中使用Canny函数实现canny边缘检测

函数原型

void Canny(InputArray image, OutputArray edges, double threshold,double threshold2,int apertureSize = 3,bool L2gradient = false)

函数参数

image:输入图片

edges:输出图片

threshold1:第一个滞后性阈值

threshold2:第二个滞后性阈值

apertureSize:表示应用Sobel算子的孔径大小,默认值为3

L2gradient:一个计算图像梯度幅值的标识,默认值false

 五:物体轮廓线[特征标记]

轮廓线提取:感兴趣的目标从图像中提取出来,通过颜色或纹理提取出目标的前景图。

轮廓线提取步骤

1、获取灰度图

2、得到二值数据

3、降噪

4、提取轮廓线

轮廓线提取方法

OpenCV使用findContours函数来提取图像中的轮廓。

函数原型

def findContours( InputArray image, OutputArrayOfArrays contours,int mode, int method, Point offset = Point())

函数参数

image:8比特单通道的源二值图像

contours:查找到的轮廓

mode:检索模式

method:边缘近视算法

本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
THE END
分享
二维码
< <上一篇
下一篇>>