【OpenCV教程】滤波和边缘检测的过程
@TOC
1.均值滤波
1.1 卷积核形状
Mat kernal=Mat::ones(Size(ksize,ksize),CV_64F)/(ksize*ksize);1.2 API
CV_EXPORTS_W void blur( InputArray src, OutputArray dst,
Size ksize, Point anchor = Point(-1,-1),
int borderType = BORDER_DEFAULT );参数如下
src(source)
输入图片
dst(destination)
输出图片
ksize(kernal size)
卷积核宽高,必须是正奇数
anchor
滤波器中心像素位置,取(-1,-1)表示几何中心
borderType
边界填充方式,默认为黑边
1.3 效果

2.高斯滤波
2.1 卷积核形状
二维高斯函数表述为:
对应图形:

代码实现(不区分sigmaX与sigmaY)
2.2 API
参数如下
src(source)
输入图片
dst(destination)
输出图片
ksize(kernal size)
卷积核宽高。如果这个尺寸我们设其为非正数,那么OpenCV会从第五个参数sigmaSpace来计算出它来。
sigmaX
x方向上的标准差
sigmaY
y方向上的标准差。默认输入量为0,则将其设置为等于sigmaX,如果两个轴的标准差均为0,则根据输入的高斯滤波器尺寸计算标准偏差。
borderType
边界填充方式,默认为黑边
2.3 效果

3.中值滤波
3.1 原理
取滤波器内的中值作为输出,可以很好的抑制椒盐噪声
3.2 API
参数如下
src(source)
输入图片
dst(destination)
输出图片
ksize(kernal size)
卷积核边长,必须是正奇数
3.3 效果

4.高斯双边滤波
4.1 原理
双边滤波器的好处是可以做边缘保存(edge preserving),一般用高斯滤波去降噪,会较明显地模糊边缘,对于高频细节的保护效果并不明显。双边滤波器顾名思义比高斯滤波多了一个高斯方差sigma-d,它是基于空间分布的高斯滤波函数,所以在边缘附近,离的较远的像素不会太多影响到边缘上的像素值,这样就保证了边缘附近像素值的保存。但是由于保存了过多的高频信息,对于彩色图像里的高频噪声,双边滤波器不能够干净的滤掉,只能够对于低频信息进行较好的滤波。

4.2 API
参数如下
src(source)
输入图片
dst(destination)
输出图片
d
卷积核边长。如果这个值我们设其为非正数,那么OpenCV会从第五个参数sigmaSpace来计算出它来。
sigmaColor
颜色空间滤波器的sigma值。这个参数的值越大,就表明该像素邻域内有更宽广的颜色会被混合到一起,产生较大的半相等颜色区域。
sigmaSpace
坐标空间中滤波器的sigma值,坐标空间的标注方差。他的数值越大,意味着越远的像素会相互影响,从而使更大的区域足够相似的颜色获取相同的颜色。当d>0,卷积核大小已被指定且与sigmaSpace无关。否则,d正比于sigmaSpace。
borderType
边界填充方式,默认为黑边
4.3 效果

5.获取用来形态学操作的滤波器
shape:滤波器形状
ksize(kernal size):滤波器大小
anchor:滤波器中心像素位置,取(-1,-1)表示几何中心
6.腐蚀和膨胀(对二值图)
6.1 原理
腐蚀:取滤波器内的最小值作为输出
膨胀:取滤波器内的最大值作为输出
6.2 腐蚀API
参数如下
src(source)
输入图片,尽量是二值图
dst(destination)
输出图片
kernal
滤波器矩阵
anchor
滤波器中心像素位置,取(-1,-1)表示几何中心
iterations
执行erode函数的次数,默认执行一次
borderType
边界填充方式,默认为黑边
borderValue
填充边界的值
6.3 效果

6.4 膨胀API
参数如下
src(source)
输入图片,尽量是二值图
dst(destination)
输出图片
kernal
滤波器矩阵
anchor
滤波器中心像素位置,取(-1,-1)表示几何中心
iterations
执行erode函数的次数,默认执行一次
borderType
边界填充方式,默认为黑边
borderValue
填充边界的值
6.5 效果

7.形态学操作(对二值图)
7.1 API
参数如下
src(source)
输入图片,尽量是二值图
dst(destination)
输出图片
op(option)
变换类型
kernal
滤波器矩阵
anchor
滤波器中心像素位置,取(-1,-1)表示几何中心
iterations
执行erode函数的次数,默认执行一次
borderType
边界填充方式,默认为黑边
borderValue
填充边界的值
7.2 变换类型
7.3 开
原理
对输入图片先进行腐蚀,然后进行膨胀。可以用来屏蔽与滤波器大小相当的亮部。
效果

7.4 闭
原理
对输入图片先进行膨胀,然后进行腐蚀。可以用来屏蔽与滤波器大小相当的暗部。
效果

7.5 顶帽
原理
对输入图片先进行开操作,然后原图-开操作图。可以用来提取与滤波器大小相当的亮部。
效果

7.6 黑帽
原理
对输入图片先进行闭操作,然后闭操作图-原图。可以用来提取与滤波器大小相当的暗部。
效果

7.7 形态学梯度
原理
膨胀图与腐蚀图之差。可以用来 提取边界轮廓 ,但提取效果比不上专业的边缘检测算法。
效果

7.8 击中击不中变换
原理
击中击不中变换由下面三步构成:
用结构元素B1来腐蚀输入图像
用结构元素B2来腐蚀输入图像的补集
前两步结果的与运算
结构元素B1和B2可以结合为一个元素B。例如:

结构元素:左B1(击中元素),中B2(击不中元素),右B(两者结合)
本例中,我们寻找这样一种结构模式,中间像素属于背景,其上下左右属于前景,其余领域像素忽略不计(背景为黑色,前景为白色)。然后用上面的核在输入图像中找这种结构。从下面的输出图像中可以看到,输入图像中只有一个位置满足要求。

输入二值图像

输出二值图像
8.边缘检测:选择合适的输出深度
参照以下表格
CV_8U
CV_16S/CV_32F/CV_64F
CV_16U/CV_16S
CV_32F/CV_64F
CV_32F
CV_32F/CV_64F
CV_64F
CV_64F
8.1 normalize归一化函数
参数如下
src(source)
输入数组
dst(destination)
输出数组
alpha
如果norm_type为NORM_MINMAX ,则alpha为最小值或最大值;如果norm_type为其他类型,则为归一化要乘的系数
beta
如果norm_type为NORM_MINMAX ,则beta为最小值或最大值;如果norm_type为其他类型,beta被忽略.
norm_type
归一化类型,详见下面的内容
iterations
执行erode函数的次数,默认执行一次
dtype
输出数组的深度,若输入-1则表示与src一致。如果不能判断需要的深度,则可以输入-1然后使用convertScaleAbs绝对值化,这也是最推荐的做法,而不推荐自己判断深度。
mask
掩码,用于指示函数是否仅仅对指定的元素进行操作。大小必须与src保持一致。具体用法见8.1.4
归一化类型(只介绍常用的四种)
NORM_L1
NORM_L2
NORM_INF
NORM_MINMAX(recommended)
8.2 convertScaleAbs绝对值化
参数如下
src(source)
输入图片
dst(destination)
输出图片
9.sobel(对灰度图)
9.1 卷积核形状(ksize=3)
9.2 API
参数如下
src(source)
输入图片,数据类型Mat
dst(destination)
输出图片,数据类型Mat
ddepth(destination depth)
输出图片的深度(CV_16F)
dx
x方向导数的阶数,一般取1
dy
y方向导数的阶数,一般取1
ksize(kernal size)
卷积核边长,默认为3
scale
生成图与原图的缩放比例,默认为1
delta
额外的增量,默认为0
borderType
边界填充方式,默认为黑边
9.3 流程
用cvtColor函数转灰度图
在x,y方向上分别各调用一次Sobel
用convertScaleAbs函数转换到CV_8U,否则无法显示
用addWeighted函数把两张输出图片加在一起
9.4 同时在x,y方向上调用Sobel和分开调用的效果对比

可以看到效果差了很多
10.scharr(对灰度图)
10.1 卷积核形状(ksize恒定为3)
虽然Sobel算子可以有效的提取图像边缘,但是对图像中较弱的边缘提取效果较差。因此为了能够有效的提取出较弱的边缘,需要将像素值间的差距增大,因此引入Scharr算子。Scharr算子是对Sobel算子差异性的增强,因此两者之间的在检测图像边缘的原理和使用方式上相同。
10.2 API
参数如下
src(source)
输入图片,数据类型Mat
dst(destination)
输出图片,数据类型Mat
ddepth(destination depth)
输出图片的深度(CV_16F)
dx
x方向导数的阶数,一般取1
dy
y方向导数的阶数,一般取1
scale
生成图与原图的缩放比例,默认为1
delta
额外的增量,默认为0
borderType
边界填充方式,默认为黑边
10.3 流程
用cvtColor函数转灰度图
在x,y方向上分别各调用一次Scharr
用convertScaleAbs函数转换到CV_8U,否则无法显示
用addWeighted函数把两张输出图片加在一起
11.Laplacian(对灰度图)
11.1 卷积核形状(ksize=3)
Laplacian算子的卷积核形状决定了它 对噪声非常敏感 ,因此,通常需要通过 滤波平滑处理 。
11.2 API
参数如下
src(source)
输入图片,数据类型Mat
dst(destination)
输出图片,数据类型Mat
ddepth(destination depth)
输出图片的深度(CV_16F)
scale
生成图与原图的缩放比例,默认为1
delta
额外的增量,默认为0
borderType
边界填充方式,默认为黑边
11.3 流程
用中值滤波等操作平滑处理
用cvtColor函数转灰度图
用Laplacian函数处理
用convertScaleAbs函数转换到CV_8U,否则无法显示
12.Canny(recommended)
12.1 API
参数如下
image
输入图片,数据类型Mat
edges
输出图片,数据类型Mat
threshold1
最小阈值
threshold2
最大阈值
apertureSize
Sobel卷积核的大小,默认为3。核越大,对噪声越不敏感,但是边缘检测的错误也会随之增加
L2gradient
计算图像梯度幅度的标识,默认为false,表示L1范数(直接将两个方向的导数的绝对值相加)。如果使用true,表示L2范数(两个方向的导数的平方和再开方)
高于threshold2被认为是真边界,低于threshold1被抛弃,介于二者之间,则取决于是否与真边界相连。
12.2 流程
用中值滤波等操作平滑处理
用Canny函数处理 (不支持原地运算)
12.3 效果

13.添加噪声
为了检测算法的稳定性,常常需要在图片中人为地添加一些噪声来进行检验。
13.1 椒盐噪声
src(source):输入图片 dst(destination):输出图片 num(number):噪声的个数
13.2 高斯噪声
src(source):输入图片 dst(destination):输出图片 meanValue:高斯函数均值 std(standard deviation):高斯函数标准差
随机数填充矩阵
参数如下
mat
输入输出矩阵,最多支持4通道,超过4通道先用reshape()改变结构
distType(distination type)
可选UNIFORM 或 NORMAL,分别表示均匀分布和高斯分布
a
disType是UNIFORM,a表示下界(闭区间);disType是NORMAL,a表示均值
b
disType是UNIFORM,b表示上界(开区间);disType是NORMAL,b表示标准差
saturateRange
只针对均匀分布有效。当为真的时候,会先把产生随机数的范围变换到数据类型的范围,再产生随机数;如果为假,会先产生随机数,再进行截断到数据类型的有效区间。
最后更新于
这有帮助吗?