Datawhale_计算机视觉基础_图像处理(7)——边缘检测及opencv实现

一、什么是边缘检测&如何边缘检测

什么是边缘:
边缘是图像强度函数快速变化的地方
如何检测边缘:
为了检测边缘,我们需要检测图像中的不连续性,可以使用导数来检测不连续性。但是,导数也会受到噪声的影响,因此 建议在求导数之前先对图像进行平滑处理。 然后我们可以使用遮罩使用卷积来检测边缘。

二、算法理论简介

2.1 Sobel算子

中心点 f(x, y) 是重点考虑的,它的权重应该多一些,所以改进成下面这样的

                -1, 0, 1

                -2, 0, 2

                -1, 0, 1

这就是 Sobel 边缘检测算子,偏 x 方向的。同理可得偏y方向上的。

                -1, -2, -1

                0,  0,  0

                1,  2,  1

分别计算偏 x 方向的 Gx,偏 y 方向的 Gy,求绝对值,压缩到 [0, 255]区间,即 G(x, y) = Gx + Gy 就是 sobel 边缘检测后的图像了。因此sobel算子是有两个方向的。

2.2 canny

canny算子的计算步骤如下:

高斯滤波目的
1.高斯滤波去噪声降低错误率
2.计算梯度幅值和方向(一阶差分偏导)估计每一点处的边缘强度与方向(sobel)
3.非极大值抑制(NMS)对Sobel、Prewitt等算子的结果进一步细化,把不是极值的点,全部置0,去掉了大部分弱的边缘。所以图像边缘会变细
4应用双阈值(Double-Threshold)检测确定真实的和可能的边缘。

三、opencv实现

3.1 Sobel算子

"""
cv2.Sobel(src, #参数是需要处理的图像;
	     ddepth, #图像的深度,-1表示采用的是与原图像相同的深度。目标图像的深度必须大于等于原图像的深度
        dx, #dx和dy表示的是求导的阶数,0表示这个方向上没有求导,一般为0、1、2。
	    dy[, 
		 dst[, #输出图片
          ksize[,#Sobel算子的大小,必须为1、3、5、7。
          scale[, #缩放导数的比例常数,默认情况下没有伸缩系数;
          delta[, #可选的增量,将会加到最终的dst中,同样,默认情况下没有额外的值加到dst中;
          borderType #判断图像边界的模式。这个参数默认值为cv2.BORDER_DEFAULT。
          ]]]]])  
"""

img =  cv2.imread(pic_fil, cv2.IMREAD_UNCHANGED) 
img= cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)

sobelx = cv2.Sobel(img, ddepth=cv2.CV_64F, dx=1, dy=0, ksize=5)
sobely = cv2.Sobel(img, ddepth=cv2.CV_64F, dx=0, dy=1, ksize=5)

#画图
fig, axes = plt.subplots(1, 3 , figsize=(10,5))
axes[0].imshow(img,cmap = 'gray')
axes[0].set_title('original')
axes[1].imshow(sobelx,cmap = 'gray')
axes[1].set_title('Sobel X')
axes[2].imshow(sobely,cmap = 'gray')
axes[2].set_title('Sobel Y')

plt.show()

在这里插入图片描述

3.2 Canny算法

"""
cv2.Canny(image,            # 输入原图(必须为单通道图)
          threshold1,
          threshold2,       # 较大的阈值2用于检测图像中明显的边缘
          [, edges[,
          apertureSize[,    # apertureSize:Sobel算子的大小
          L2gradient ]]])   # 参数(布尔值):
                              true: 使用更精确的L2范数进行计算(即两个方向的倒数的平方和再开放),
                              false:使用L1范数(直接将两个方向导数的绝对值相加)。
"""
# canny边缘检测
img1 = cv2.GaussianBlur(img,(3,3),0)
canny = cv2.Canny(img1, 50, 150)

# 二值化将图片翻转 突出线条 
temp_dark = cv2.adaptiveThreshold(canny, maxValue=255
                         ,adaptiveMethod = cv2.ADAPTIVE_THRESH_GAUSSIAN_C
                         ,thresholdType = cv2.THRESH_BINARY
                         ,blockSize = 5
                         ,C = 5
                         )

fig, axes = plt.subplots(1, 3 , figsize=(10,5))
axes[0].imshow(img,cmap = 'gray')
axes[0].set_title('original')
axes[1].imshow(canny,cmap = 'gray')
axes[1].set_title('canny')
axes[2].imshow(temp_dark,cmap = 'gray')
axes[2].set_title('canny adaptiveThreshold')
plt.show()

在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Scc_hy

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值