CV总结之边缘检测

news/2024/11/30 11:50:49/文章来源:https://www.cnblogs.com/ljt1412451704/p/18578239

边缘检测

常见算子

边缘检测是图像处理和计算机视觉中的一个基本任务,目的是识别图像中物体的边界。边缘是图像中亮度变化显著的区域,通常标志着物体、表面或形状的边界。边缘检测对于后续的图像分析任务,如特征提取、目标识别和图像分割等,都是非常重要的。

常见边缘检测算法:

  1. Roberts算子:基于对角线方向的差分,使用两个2x2的卷积核来检测边缘。
  2. Prewitt算子:使用3x3的卷积核,对图像进行水平和垂直方向的差分,以检测边缘。
  3. Sobel算子:也是基于3x3的卷积核,但设计得更加精细,可以同时检测水平和垂直方向的边缘。
  4. Kirsch算子:使用8个不同方向的3x3卷积核来检测边缘,可以检测8个方向上的边缘。
  5. Robinson算子:类似于Kirsch算子,使用8个3x3的卷积核,但核的值有所不同。
  6. Canny算子:被认为是最优秀的边缘检测算子之一,它通过高斯滤波、梯度计算、非极大值抑制和双阈值检测等步骤来检测边缘。
  7. Laplacian算子:基于二阶导数,用于检测图像中的边缘,但对噪声较为敏感。
  8. Zero-Crossing算子:基于拉普拉斯算子,通过检测拉普拉斯算子的零交叉点来确定边缘位置。
  9. Shen-Castan滤波器:结合了Canny算子和Laplacian算子的特点,通过非线性映射和阈值处理来检测边缘。
  10. 结构化森林:一种较新的边缘检测方法,使用深度学习技术来检测边缘。

边缘检测算法的选择:

  • 简单性:对于需要快速响应的应用,可能会选择Roberts、Prewitt或Sobel算子。
  • 准确性:对于需要高精度边缘检测的应用,Canny算子通常是首选。
  • 抗噪声能力:Canny算子和结构化森林等算法具有较强的抗噪声能力。
  • 计算资源:对于计算资源有限的情况,可能会选择计算量较小的算法。

每种算法都有其特定的应用场景和优缺点,选择合适的算法需要根据具体的应用需求和条件来决定。

Canny算子

Canny算子是一种经典的边缘检测算法,由John F. Canny在1986年提出。它的目标是在保留图像原有属性的同时,显著减少图像的数据规模,找到最优的边缘检测解。Canny算子以其准确性高、低错误率、单一性和高效性而闻名,被广泛应用于各种计算机视觉系统中。以下是Canny算子的主要步骤和特点:

  1. 高斯滤波去噪:Canny算法的第一步是使用高斯滤波器平滑图像,以去除噪声。噪声和边缘都属于高频信号,高斯模糊可以减少噪声对边缘检测的影响。高斯核的大小会影响边缘检测的性能,核越大,对噪声的抑制越强,但边缘的定位误差也可能增加。
  2. 计算梯度强度和方向:Canny算法使用Sobel算子来计算图像的梯度幅度和方向。梯度的方向通常与边缘垂直,梯度的方向被归为四类:垂直、水平和两个对角线(即,0度、45度、90度和135度四个方向)。
  3. 非极大值抑制:在计算出梯度幅度和方向后,Canny算子通过非极大值抑制技术来过滤掉非边缘像素,使得边缘更加清晰。这个过程保留了每个像素点上梯度强度的极大值,过滤掉其他的值。
  4. 双阈值检测:经过非极大值抑制后,图像中仍然有很多噪声点。Canny算法使用双阈值技术,设定一个阈值上界和阈值下界,大于上界的认为是强边缘,小于下界的不是边缘,两者之间的是候选项(弱边缘),需进行进一步处理。
  5. 滞后技术跟踪边缘:最后,Canny算子使用滞后技术来跟踪边缘。如果某一像素位置和强边界相连的弱边界则认为是边缘,其他的弱边界则被删除。

Canny算子的优势在于其能够准确地找到图像中真实的边缘位置,并能够将边缘与噪声区分开,同时保持边缘的连续性和精确性。它适用于实时边缘检测,并且在MATLAB、OpenCV等常用图像处理工具中已有内置的Canny算子API。

使用OpenCV进行Canny边缘检测的Python代码如下:

首先,确保你已经安装了OpenCV库。如果没有安装,可以通过pip安装:

 
 
 
xxxxxxxxxx
 
 
 
 
pip install opencv-python
 

然后,你可以使用以下代码进行边缘检测:

 
 
 
xxxxxxxxxx
 
 
 
 
import cv2
import numpy as np
from matplotlib import pyplot as plt

# 读取图像(注意路径替换,并使用`cv2.IMREAD_GRAYSCALE`参数以灰度模式读取图像)
image = cv2.imread('path_to_your_image.jpg', cv2.IMREAD_GRAYSCALE)

# 检查图像是否成功加载
if image is None:
    print("Error: Image not found")
else:
    # 应用高斯模糊,减少图像噪声,有助于Canny算子更准确地检测边缘。
    blurred_image = cv2.GaussianBlur(image, (5, 5), 0)

    # 使用Canny算子检测边缘
    # 参数分别为:高阈值和低阈值(阈值决定了哪些边缘被认为是真实的边缘)
    edges = cv2.Canny(blurred_image, 50, 150)

    # 显示原图和边缘检测结果
    plt.figure(figsize=(10, 5))
    plt.subplot(121), plt.imshow(image, cmap='gray')
    plt.title('Original Image'), plt.xticks([]), plt.yticks([])
    plt.subplot(122), plt.imshow(edges, cmap='gray')
    plt.title('Edge Image'), plt.xticks([]), plt.yticks([])

    # 显示图像
    plt.show()
 

Kirsch算子

Kirsch算子是一种边缘检测算法,由R. Kirsch提出。它通过使用8个特定的3x3模板对图像进行卷积操作来检测边缘,这些模板代表了8个不同的方向,能够对图像上的8个特定边缘方向作出最大响应。在运算中,取这8个方向的最大值作为图像的边缘输出。

Kirsch算子的特点:

  1. 多方向响应:Kirsch算子的8个模板可以检测图像中的多个方向的边缘,这使得它在保持细节和抗噪声方面都有较好的效果。
  2. 边缘强度与方向:在计算边缘强度的同时可以得到边缘的方向,各方向间的夹角为45º。
  3. 最大响应值:对于图像上的每一个像素点,Kirsch算子通过卷积求导数,并取8个方向中的最大值作为该点的边缘输出。

Kirsch算子的模板:

Kirsch算子的8个模板如下所示,每个模板对应一个特定的方向,用于检测该方向上的边缘强度:

image-20241130111305623

这些模板通过与图像进行卷积操作来计算每个像素点的梯度幅度,然后选择最大梯度幅度的方向作为该点的边缘方向。Kirsch算子在图像处理领域,尤其是在边缘检测方面,因其有效性和鲁棒性而被广泛应用。

根据搜索结果,以下是使用Python和OpenCV实现Kirsch算子进行边缘检测的代码示例:

 
 
 
xxxxxxxxxx
 
 
import cv2
import numpy as np
from matplotlib import pyplot as plt

# 读取图像
image = cv2.imread('path_to_your_image.jpg', cv2.IMREAD_GRAYSCALE)

# 检查图像是否成功加载
if image is None:
    print("Error: Image not found")
else:
    # 自定义Kirsch算子的8个卷积核
    m1 = np.array([[5, 5, 5], [-3, 0, -3], [-3, -3, -3]])
    m2 = np.array([[-3, 5, 5], [-3, 0, 5], [-3, -3, -3]])
    m3 = np.array([[-3, -3, 5], [-3, 0, 5], [-3, -3, 5]])
    m4 = np.array([[-3, -3, -3], [-3, 0, 5], [-3, 5, 5]])
    m5 = np.array([[-3, -3, -3], [-3, 0, -3], [5, 5, 5]])
    m6 = np.array([[-3, -3, -3], [5, 0, -3], [5, 5, -3]])
    m7 = np.array([[5, -3, -3], [5, 0, -3], [5, -3, -3]])
    m8 = np.array([[5, 5, -3], [5, 0, -3], [-3, -3, -3]])
    filterlist = [m1, m2, m3, m4, m5, m6, m7, m8]  # 将各个方向的卷积核放到一起便于统一操作

    # 建立三维数组,第0维表示各个方向卷积后的值
    filtered_list = np.zeros((8, image.shape[0], image.shape[1]))

    # 对图像进行卷积操作
    for k in range(8):
        out = cv2.filter2D(image, cv2.CV_16S, filterlist[k])
        filtered_list[k] = out

    # 取八个方向中的最大值作为图像该点滤波之后的新的像素值
    final = np.max(filtered_list, axis=0)

    # 将像素值大于255的点等于255,小于255的点等于0
    final[np.where(final >= 255)] = 255
    final[np.where(final < 255)] = 0

    # 显示原图和边缘检测结果
    plt.figure(figsize=(10, 5))
    plt.subplot(121), plt.imshow(image, cmap='gray')
    plt.title('Original Image'), plt.xticks([]), plt.yticks([])
    plt.subplot(122), plt.imshow(final, cmap='gray')
 
 
    plt.title('Edge Image'), plt.xticks([]), plt.yticks([])

    # 显示图像
    plt.show()
 

Kirsch算子和Canny算子区别

Kirsch算子和Canny算子都是图像处理中用于边缘检测的算法,但它们在实现和特点上存在一些区别:

  1. 原理和方法

    • Kirsch算子:基于一阶导数的方法,使用8个方向的卷积核来检测边缘,每个卷积核对应一个方向,能够检测8个方向的边缘强度。
    • Canny算子:非微分边缘检测算子,它是一个多阶段的优化算子,包括高斯滤波、梯度计算、非极大值抑制和双阈值检测等步骤。
  2. 对噪声的敏感性

    • Kirsch算子:由于考虑了多个方向的像素突变,对噪声的抑制能力不如Canny算子,锐化效果可能不是很理想。
    • Canny算子:首先使用高斯滤波器平滑图像以去除噪声,因此对噪声不敏感,不容易受到噪声干扰。
  3. 边缘定位

    • Kirsch算子:边缘定位不如Canny算子精确,因为它是基于一阶导数的,而Canny算子结合了梯度的方向和幅度。
    • Canny算子:边缘定位较准确,常用于噪声较多,灰度渐变的图像。
  4. 计算复杂度

    • Kirsch算子:由于使用了8个卷积核,计算复杂度相对较高。
    • Canny算子:虽然实现较为复杂,但通常被认为是最有效的边缘检测方法之一,尤其是在实际项目如车道线检测中。
  5. 应用场景

    • Kirsch算子:适用于简单场景下的边缘检测,尤其是当需要快速响应时。
    • Canny算子:被广泛用于诸如车道线检测等实际项目中,是最有效的边缘检测方法之一。

总的来说,Canny算子在边缘检测的准确性、鲁棒性以及对噪声的抑制方面表现更好,而Kirsch算子则在计算速度上可能有一定优势,尤其是在对实时性要求较高的应用中。

结构化森林

结构化森林(Structured Forests)是一种基于深度学习的边缘检测方法,它在图像处理领域中被用来快速且有效地识别图像中的边缘。以下是结构化森林的一些关键特点和应用场景:

  1. 快速边缘检测:结构化森林能够快速预测局部掩模的边缘,这对于实时或近实时的边缘检测应用非常有用。
  2. 深度学习的应用:结构化森林结合了深度学习技术,通过训练一个结构化的随机森林模型来识别图像中的边缘。这种方法可以处理复杂的图像特征,并在多种场景下表现出良好的性能。
  3. 提高检测准确性:结构化森林在实验中显示出,它不仅提高了检测的准确性,而且减少了计算时间。这对于需要高效边缘检测的应用场景非常重要。
  4. 复杂背景下的应用:在复杂相似背景下,结构化森林能够有效地区分相似和随机的裂缝特征,这对于结构健康监测等领域尤为重要。
  5. 与其他算法的结合:结构化森林可以与其他图像处理技术结合使用,例如与Hough变换结合用于海天线检测。这种方法可以较好地忽略局部干扰边缘,强化边界提取,对复杂海天背景下的海天线检测具备鲁棒性和高准确性。
  6. OpenCV中的实现:在OpenCV库中,结构化森林被实现为一个快速的边缘检测工具。它可以通过提供预训练的模型文件来使用,这个模型文件可以在GitHub的opencv_extra仓库中找到。
  7. 代码实现:在实际应用中,结构化森林的边缘检测可以通过几行代码实现。首先,需要将输入图像转换为浮点类型,并除以255进行归一化。然后,使用createStructuredEdgeDetection函数创建一个边缘检测对象,并调用detectEdges方法来检测边缘。最后,可以通过非极大值抑制(NMS)进一步处理边缘图,以得到更清晰的边缘。

结构化森林因其快速、准确和在复杂背景下的有效性,成为了边缘检测领域中一个有前景的方法。

在OpenCV中,结构化森林(Structured Forests)边缘检测可以通过以下步骤进行调用和实现。这里提供一个简单的Python代码示例,展示如何使用OpenCV中的结构化森林进行边缘检测:

 
 
 
x
 
 
 
 
import cv2
import numpy as np

# 读取图像 (注意路径替换,并使用`cv2.IMREAD_GRAYSCALE`参数以灰度模式读取图像)
image = cv2.imread('path_to_your_image.jpg', cv2.IMREAD_GRAYSCALE)

# 检查图像是否成功加载
if image is None:
    print("Error: Image not found")
else:
    # 创建结构化森林边缘检测器
    structured_forest = cv2.createStructuredEdgeDetection()

    # 检测边缘
    edges = structured_forest.detectEdges(image)

    # 应用非极大值抑制(NMS)来细化边缘
    # flags=cv2.Canny_NORM_L2_GRADIENT来应用非极大值抑制,这有助于细化边缘。
    edges_nms = structured_forest.detectEdges(image,                                                           flags=cv2.Canny_NORM_L2_GRADIENT)

    # 显示原始图像和边缘检测结果
    cv2.imshow('Original Image', image)
    cv2.imshow('Edges', edges)
    cv2.imshow('Edges NMS', edges_nms)

    # 等待按键后关闭窗口
    cv2.waitKey(0)
    cv2.destroyAllWindows()
 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/844090.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

C# mvc +axios + web api + javascript

2024年,是Insus.NET生命中转折的一年,许久没有更新博客了。许多网友在通讯或邮件私聊,希望在博客上更新内容,分享一些技能与通用的博文。回归正题,在C# mvc使用javascript axios访问web api。 在ms sql server创建数据表 存储过程... C# MVC程序与数据库交互,创建entit…

cron: 如何使用Cron表达式配置定时任务

Cron表达式用于设置定时任务,无论是在Linux的Crontab中,还是在各种语言开发的程序中都有应用,它提供了一种强大而灵活的方法来设定定时任务。 Cron表达式语法 Cron表达式是一种字符串格式,标准的Cron表达式是由五部分组成,分别表示,分钟、小时、日期、月份和星期几。这个…

[C++][MSVC][Error] 检测到 RuntimeLibrary 的不匹配项: 值 MT_StaticRelease 不匹配值 MD_DynamicRelease

1 简介 本文将介绍在 C++ 编程中使用 MSVC 编译器时可能遇到的错误:检测到 RuntimeLibrary 的不匹配项:值 MT_StaticRelease 不匹配值 MD_DynamicRelease。该错误通常是由于编译器和链接器之间的设置不一致引起的。 2 VisualStudio环境 在 MSVC 工程上右键->属性,找到配置…

ChatRoom pg walkthrough Intermediate

NMAP ┌──(root㉿kali)-[~/lab] └─# nmap -p- -A 192.168.189.110 Starting Nmap 7.94SVN ( https://nmap.org ) at 2024-11-30 00:22 UTC Nmap scan report for 192.168.189.110 Host is up (0.073s latency). Not shown: 65533 filtered tcp ports (no-response) PORT …

vxe-table 树形表格的用法详解

vxe-table 树形表格的使用,支持多种数据结构,可以是带有父子结构的数组,也可以带有层级结构的嵌套数据。 官网:https://vxetable.cn Gitee 带有父子结构的平级数据 只需要带有父子结构的平级数据,例如:id 和 parentId,字段名可以任意设置。对于保存到数据库的平级数据非…

电动车头盔穿戴检测方案

电动车头盔穿戴检测方案的核心在于利用现场监控摄像头捕捉道路上骑电动车、三轮车等骑行者的状态,电动车头盔穿戴检测方案通过深度学习算法自动识别骑行者是否佩戴了安全头盔。在实施过程中,监控摄像头会持续捕捉路面情况,并将图像数据传输至后端服务器(也可以前端分析,本…

滑坡监测识别摄像头

滑坡监测识别摄像头安装在潜在滑坡区域,滑坡监测识别摄像头通过捕捉实时图像,对这些图像进行深度分析,识别出可能的滑坡迹象。一旦系统检测到异常,它将立即发出预警信号,通知相关部门采取紧急措施,从而减少灾害带来的损失。滑坡监测识别摄像头的智能预警系统,不仅提高了…

人员跌倒检测摄像头

人员跌倒检测摄像头的核心在于其搭载的深度学习算法,人员跌倒检测摄像头采用了先进的YOLOX结合OpenCV,能够高效地对视频流进行实时分析和处理,当摄像头检测到有人跌倒时,它会自动对跌倒者进行抓拍,并将当时的图像传输到管理中心。这一过程无需人工干预,大大提高了响应速度…

深度学习发展历史

https://www.bookstack.cn/read/paddlepaddle-tutorials/spilt.3.3d52d8126c99cb7b.md 作者:太一吾鱼水 宣言:在此记录自己学习过程中的心得体会,同时积累经验,不断提高自己! 声明:博客写的比较乱,主要是自己看的。如果能对别人有帮助当然更好,不喜勿喷! …

Latex添加一条水平线——overleaf可以用

https://blog.csdn.net/qq_46753404/article/details/118083320 效果如下:添加水平线语法 {\noindent} \rule[-10pt]{17.5cm}{0.05em}\\ {\noindent} 表示取消缩进 \rule[水平高度]{长度}{粗细}

Latex高亮文本,简单有效——overleaf也可以用

https://blog.csdn.net/ShuqiaoS/article/details/118217508 普通文本高亮 效果是这样的:首先在开头使用: \usepackage{soul, color, xcolor} 之后在需要高亮的地方使用: \hl{文本} (注意,如果应用了\hl但是没有反应或者高亮有问题,多半是由于没有包含color和xcolor的缘故…