zoukankan      html  css  js  c++  java
  • 【DW打卡-计算机视觉基础】06 边缘检测

    6.1 简介

    GitHub:https://github.com/QiangZiBro

    6.1.1 什么是边缘?

    边缘是图像强度函数快速变化的地方

    完成一个Canny边缘检测算法可以分为以下四步:

    高斯滤波 目的
    1.高斯滤波 去噪声降低错误率
    2.计算梯度幅值和方向 估计每一点处的边缘强度与方向
    3.非极大值抑制(NMS) 对Sobel、Prewitt等算子的结果进一步细化
    4应用双阈值(Double-Threshold)检测 确定真实的和可能的边缘。

    1.高斯滤波

    边缘检测结果容易受到图像噪声的影响,图片中一些噪声会大大影像边缘检测。因此为了使图像平滑,可以用高斯滤波器内核与图像进行卷积。 此步骤将使图像稍微平滑,以减少边缘检测器上明显噪声的影响。

    2.计算梯度强度和方向

    进行高斯滤波后,图像中的边缘可以指向各个方向,接下来使用四个算子来检测图像中的水平、垂直和对角边缘。

    3.非极大值抑制(NMS)

    在每一点上,邻域中心与沿着其对应的梯度方向的两个像素相比,若中心像素为最大值,则保留,否则中心置0,这样可以抑制非极大值,保留局部梯度最大的点,以得到细化的边缘。

    非极大值抑制是一种边缘稀疏技术,非极大值抑制的作用在于“瘦”边。

    4. 用双阈值算法检测和连接边缘

    一张图解释双阈值算法检测:

    6.5 基于OpenCV的实现

    6.5.1 Sobel算子 & 6.5.2 Canny算法

    
    import cv2
    import numpy as np
    from matplotlib import pyplot as plt
    
    if __name__ == '__main__':
    
        # IMREAD_GRAYSCALE  0
        # cv2.IMREAD_UNCHANGED  -1
        img = cv2.imread('./00_dog.jpg', 0)
    
        """
            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。
                  ]]]]])  
        """
    
        #读图
        sobelx = cv2.Sobel(img,cv2.CV_64F,1,0,ksize=5)
        sobely = cv2.Sobel(img,cv2.CV_64F,0,1,ksize=5)
    
        #画图
        plt.subplot(1,3,1),plt.imshow(img,cmap = 'gray')
        plt.title('Original'), plt.xticks([]), plt.yticks([])
    
        plt.subplot(1,3,2),plt.imshow(sobelx,cmap = 'gray')
        plt.title('Sobel X'), plt.xticks([]), plt.yticks([])
    
        plt.subplot(1,3,3),plt.imshow(sobely,cmap = 'gray')
        plt.title('Sobel Y'), plt.xticks([]), plt.yticks([])
    
        plt.show()
    
    
        """
        cv2.Canny(image,            # 输入原图(必须为单通道图)
                  threshold1,
                  threshold2,       # 较大的阈值2用于检测图像中明显的边缘
                  [, edges[,
                  apertureSize[,    # apertureSize:Sobel算子的大小
                  L2gradient ]]])   # 参数(布尔值):
                                      true: 使用更精确的L2范数进行计算(即两个方向的倒数的平方和再开放),
                                      false:使用L1范数(直接将两个方向导数的绝对值相加)。
        """
    
        original_img = img.copy()
    
        # canny边缘检测
        img1 = cv2.GaussianBlur(original_img,(3,3),0)
        canny = cv2.Canny(img1, 50, 150)
    
        # 画图
        plt.subplot(1,2,1),plt.imshow(original_img,cmap = 'gray')
        plt.title('Original'), plt.xticks([]), plt.yticks([])
    
        plt.subplot(1,2,2),plt.imshow(canny,cmap = 'gray')
        plt.title('Canny'), plt.xticks([]), plt.yticks([])
        plt.show()
    

    展示效果


    你不逼自己一把,你永远都不知道自己有多优秀!只有经历了一些事,你才会懂得好好珍惜眼前的时光!
  • 相关阅读:
    Leetcode: Longest Increasing Subsequence
    Leetcode: Bulls and Cows
    Leetcode: Serialize and Deserialize Binary Tree
    undefined reference to symbol '_ZNK11GenICam_3_016GenericException17GetSourceFileNameEv'
    ranlib 作用
    live555运行时报错:StreamParser internal error ( 86451 + 64000 > 150000)
    qt 免注册下载
    modsign: could't get uefi db list
    ubuntu安装 opencv-3.4.3
    xl2tpd[26104]: Maximum retries exceeded for tunnel 33925. Closing
  • 原文地址:https://www.cnblogs.com/zhazhaacmer/p/15328153.html
Copyright © 2011-2022 走看看