Opencv之图像边缘检测:2.Scharr算子(cv2.Scharr)

2.1 原理介绍:  

        在离散的空间上,有很多方法可以用来计算近似导数,在使用3×3的Sobel算子时,可能计算结果并不太精准。OpenCV提供了Scharr算子,该算子具有和Sobel算子同样的速 度,且精度更高。可以将Scharr算子看作对Sobel算子的改进,其核通常为:

        

2.2 函数语法:

        OpenCV提供了函数cv2.Scharr()来计算Scharr算子,其语法格式如下:

        dst=cv2.Scharr(src,ddepth,dx,dy[,scale[,delta[,borderType]]])

        式中:

        ● dst代表输出图像。

        ● src代表原始图像。

        ● ddepth代表输出图像深度。该值与函数cv2.Sobel()中的参数ddepth的含义相同。

        ● dx代表x方向上的导数阶数。

        ● dy代表y方向上的导数阶数。

        ● scale代表计算导数值时的缩放因子,该项是可选项,默认值是1,表示没有缩放。

        ● delta代表加到目标图像上的亮度值,该项是可选项,默认值为0。

        ● borderType代表边界样式。

        在函数cv2.Sobel()中介绍过,如果ksize=-1,则会使用Scharr滤波器。 因此,如下语句:dst=cv2.Scharr(src,ddepth,dx,dy)和 dst=cv2.Sobel(src,ddepth,dx,dy,-1) 是等价的。

        函数cv2.Scharr()和函数cv2.Sobel()的使用方式基本一致。 首先,需要注意的是,参数ddepth的值应该设置为“cv2.CV_64F”,并对函数 cv2.Scharr()的计算结果取绝对值,才能保证得到正确的处理结果。

        另外,需要注意的是,在函数cv2.Scharr()中,要求参数dx和dy满足条件:

        dx >=0 && dy >=0 && dx+dy==1

        因此,参数dx和参数dy的组合形式有:

        ● 计算x方向边缘(梯度):dx=1,dy=0。

        ● 计算y方向边缘(梯度): dx=0,dy=1。

        ● 计算x方向与y方向的边缘叠加:通过组合方式实现。

2.3 程序示例

import cv2  as cv

def cv_show(name, img):
    cv.imshow(name, img)
    cv.waitKey(0)
    cv.destroyAllWindows()

img = cv.imread('D:\\qipan.jpg')
if img is None:
    print('Failed to read the image')

# x方向边缘检测
img1 = cv.Scharr(img, cv.CV_64F, 1, 0)
scharrx = cv.convertScaleAbs(img1)
cv_show('scharrx', scharrx)

# y方向边缘检测
img2 = cv.Scharr(img, cv.CV_64F, 0, 1)
scharry = cv.convertScaleAbs(img2)
cv_show('scharry', scharry)

# 需要注意的是,参数dx和dy的值不能都为1。例如,如下语句是错误的:
# dst=Scharr(src,ddpeth,dx=1,dy=1)

scharr = cv.addWeighted(scharrx, 0.5, scharry, 0.5, 0)
cv_show('scharr', scharr)

原图如下:

 x方向边缘检测:

 y方向边缘检测:

 x,y方向叠加效果:

 

猜你喜欢

转载自blog.csdn.net/qq_49478668/article/details/123742957