什么是用于Sobel边缘检测的Matlab代码的OpenCv等价物?

时间:2018-04-09 04:50:05

标签: python matlab opencv

这是我想在OpenCv中复制的Matlab代码

e[~, threshold] = edge(I, 'sobel');
fudgeFactor = .5;
BWs = edge(I,'sobel', threshold * fudgeFactor);
figure, imshow(BWs), title('binary gradient mask');

这是我的测试图片:

Cell image

我尝试过像

这样的事情
blurred_gray = cv2.GaussianBlur(gray_image,(3,3),0)
sobelx = cv2.Sobel(blurred_gray,cv2.CV_8U,1,0,ksize=3) 
sobely = cv2.Sobel(blurred_gray,cv2.CV_8U,0,1,ksize=3)[2]

我得到的输出是:

sobelx

sobely

我尝试添加sobelx和sobely,因为我读到它们是偏导数,但结果图像看起来与上面相同,并且改变ksize没有帮助。

这是我需要的输出:

edge image

有人可以告诉我我做错了什么以及我应该做些什么来获得相同的结果图像?

1 个答案:

答案 0 :(得分:3)

sobel边缘检测的MATLAB实现是不可见的,所以我们只能猜测到底发生了什么。我们得到的唯一提示是edge上的文档说明当使用'sobel'选项时

  

在图像I的渐变点处找到边缘   最大,使用Sobel逼近导数。

没有说明,但是采用最大梯度比仅仅采用图像中的局部最大值更复杂。相反,我们希望找到相对于梯度方向的局部最大值。不幸的是,MATLAB用于此操作的实际代码是隐藏的。

查看edge中可用的代码,看起来他们在细化操作中使用4 * mean(幅度)作为阈值,因此我将此与您的软糖因子结合使用。 orientated_non_max_suppression函数远非最优,但我是为了提高性能而编写的。

import cv2
import numpy as np
import scipy.ndimage.filters

gray_image = cv2.imread('cell.png', cv2.IMREAD_GRAYSCALE).astype(dtype=np.float32)

def orientated_non_max_suppression(mag, ang):
    ang_quant = np.round(ang / (np.pi/4)) % 4
    winE = np.array([[0, 0, 0],
                     [1, 1, 1],
                     [0, 0, 0]])
    winSE = np.array([[1, 0, 0],
                      [0, 1, 0],
                      [0, 0, 1]])
    winS = np.array([[0, 1, 0],
                     [0, 1, 0],
                     [0, 1, 0]])
    winSW = np.array([[0, 0, 1],
                      [0, 1, 0],
                      [1, 0, 0]])

    magE = non_max_suppression(mag, winE)
    magSE = non_max_suppression(mag, winSE)
    magS = non_max_suppression(mag, winS)
    magSW = non_max_suppression(mag, winSW)

    mag[ang_quant == 0] = magE[ang_quant == 0]
    mag[ang_quant == 1] = magSE[ang_quant == 1]
    mag[ang_quant == 2] = magS[ang_quant == 2]
    mag[ang_quant == 3] = magSW[ang_quant == 3]
    return mag

def non_max_suppression(data, win):
    data_max = scipy.ndimage.filters.maximum_filter(data, footprint=win, mode='constant')
    data_max[data != data_max] = 0
    return data_max

# compute sobel response
sobelx = cv2.Sobel(gray_image, cv2.CV_32F, 1, 0, ksize=3)
sobely = cv2.Sobel(gray_image, cv2.CV_32F, 0, 1, ksize=3)
mag = np.hypot(sobelx, sobely)
ang = np.arctan2(sobely, sobelx)
# threshold
fudgefactor = 0.5
threshold = 4 * fudgefactor * np.mean(mag)
mag[mag < threshold] = 0
# non-maximal suppression
mag = orientated_non_max_suppression(mag, ang)
# alternative but doesn't consider gradient direction
# mag = skimage.morphology.thin(mag.astype(np.bool)).astype(np.float32)

# create mask
mag[mag > 0] = 255
mag = mag.astype(np.uint8)

细胞结果

<强>的Python

enter image description here

<强> MATLAB

enter image description here

MATLAB&#39; peppers.png(内置)

的结果

<强>的Python

enter image description here

<强> MATLAB

enter image description here

MATLAB实现必须使用一些不同的东西,但看起来这非常接近。