当前位置: 首页 > news >正文

《opencv实用探索·十一》opencv之Prewitt算子边缘检测,Roberts算子边缘检测和Sobel算子边缘检测

1、前言

边缘检测:
图像边缘检测是指在图像中寻找灰度、颜色、纹理等变化比较剧烈的区域,它们可能代表着物体之间的边界或物体内部的特征。边缘检测是图像处理中的一项基本操作,可以用于人脸识别、物体识别、图像分割等多个领域。

边缘检测实质上是计算当前点和周围点灰度的差别。

图像边缘检测流程主要分为以下几个步骤:
(1)读取待处理图像;
(1)图像滤波,例如使用高斯滤波器,平滑图像,去除噪声;
(2)计算图像中每个像素点的梯度强度和方向;
(3)应用非极大值抑制(Non-Maximum Suooression),保留梯度方向上的局部最大值,抑制非边缘点,消除边缘检测带来的杂散响应;
(4)应用双阈值(Double-Threshold)检测来确定真实的和潜在的边缘,即将梯度幅值映射到两个阈值,根据梯度值高于高阈值或在高低阈值之间的情况,将像素标记为强边缘、弱边缘或非边缘。
(5)边缘连接,通过连接相邻的强边缘像素和与之相连的弱边缘像素,形成最终的边缘图像;
(6)显示结果。

在介绍各种边缘检测算子之前先简单阐述下怎么寻找边缘。

下面左图是一张黑白相间的图,右图是左图的每个像素的灰度值
在这里插入图片描述
我们设定一个卷积核如下(关于卷积的介绍请看之前的文章):
在这里插入图片描述
原图在通过卷积核进行卷积计算后得到的图像如下:
可以看到原图在卷积运算后黑色向白色突变的边缘被很好的保留了下来,因此可以通过这个卷积核找到图像中垂直的边缘。
在这里插入图片描述
同理,如果我们用下面的卷积核也可以找到图像中水平的边缘。
在这里插入图片描述
卷积运算后:
在这里插入图片描述

2、Prewitt算子边缘检测
如果我们把上面两个卷积核组合起来再对图像进行卷积便可以同时找到图像中水平和垂直的边缘,这种卷积核就是prewitt算子。
在这里插入图片描述

标准的 Prewitt 边缘检测算子由以下两个卷积核组成。
在这里插入图片描述
下面是用prewitt算子进行边缘检测的案例:

#include <opencv2/opencv.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>using namespace cv;int main() {// 读取图像Mat image = imread("your_image.jpg", IMREAD_GRAYSCALE);// 定义Prewitt算子Mat prewitt_x = (Mat_<float>(3, 3) << -1, 0, 1, -1, 0, 1, -1, 0, 1);Mat prewitt_y = (Mat_<float>(3, 3) << -1, -1, -1, 0, 0, 0, 1, 1, 1);// 对图像应用Prewitt算子Mat edges_x, edges_y;filter2D(image, edges_x, CV_64F, prewitt_x);filter2D(image, edges_y, CV_64F, prewitt_y);// 计算梯度幅值和方向Mat gradient_magnitude, gradient_direction;magnitude(edges_x, edges_y, gradient_magnitude);phase(edges_x, edges_y, gradient_direction, true);// 归一化梯度幅值cv::normalize(gradient_magnitude, gradient_magnitude, 0, 1, cv::NORM_MINMAX);// 显示结果imshow("Original Image", image);  //原灰度图imshow("Gradient Magnitude", gradient_magnitude);  //prewitt算子边缘检测图waitKey(0);destroyAllWindows();return 0;
}

代码解读:
(1)在代码中我们先分别定义一个水平方向和垂直方向的prewitt算子edges_x和edges_y
(2)filter2D是对图像进行卷积操作,即获取prewitt算子与原图像卷积后的图像edges_x和edges_y
(3)magnitude 函数的主要用途是计算两个输入数组的逐元素平方和的平方根。在图像处理中,常常用于计算图像中每个像素点的梯度幅值。相位(Phase)在图像处理中通常指的是梯度的方向(边缘方向)。在梯度计算中,梯度向量的方向表示图像在该点上灰度变化最快的方向。在梯度计算中,通常使用 magnitude 函数计算梯度的幅值,使用 phase 函数计算梯度的方向。这两个信息一起构成了梯度向量,提供了有关图像局部变化的重要信息。
(4)最后归一化梯度幅值图像,因为64位图像显示范围为0-1。

最后效果如下(左边是原灰度图,右边是边缘检测出的图像):
在这里插入图片描述

3、Roberts算子
常用来处理具有陡峭的低噪声图像,当图像边缘接近于正45度或负45度时,该算法处理效果更理想。其缺点是对边缘的定位不太准确,提取的边缘线条较粗。

下图左边为水平方向Roberts算子,也称正对角算子。右边为垂直方向Roberts算子,也称斜对角算子。
在这里插入图片描述
下面是Roberts算子的使用案例:

#include <opencv2/opencv.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>int main() {// 生成一个简单的图像cv::Mat image = cv::Mat::zeros(100, 100, CV_8U);cv::rectangle(image, cv::Rect(20, 20, 60, 60), cv::Scalar(255), cv::FILLED);// 定义Sobel算子cv::Mat sobel_x = (cv::Mat_<float>(3, 3) << -1, 0, 1, -2, 0, 2, -1, 0, 1);cv::Mat sobel_y = (cv::Mat_<float>(3, 3) << -1, -2, -1, 0, 0, 0, 1, 2, 1);// 应用Sobel算子cv::Mat edges_x, edges_y;cv::filter2D(image, edges_x, CV_64F, sobel_x);cv::filter2D(image, edges_y, CV_64F, sobel_y);// 计算梯度幅值和方向cv::Mat gradient_magnitude, gradient_direction;cv::magnitude(edges_x, edges_y, gradient_magnitude);cv::phase(edges_x, edges_y, gradient_direction, true);  // true 表示计算角度的弧度值// 归一化梯度方向到[0, 1]范围cv::normalize(gradient_direction, gradient_direction, 0, 1, cv::NORM_MINMAX);// 显示结果cv::imshow("Original Image", image);cv::imshow("Gradient Magnitude", gradient_magnitude);cv::imshow("Gradient Direction", gradient_direction);cv::waitKey(0);cv::destroyAllWindows();return 0;
}

最后效果如下(左边是原灰度图,右边是边缘检测出的图像):
在这里插入图片描述

4、Sobel算子边缘检测
Sobel算子在Prewitt算子的基础上增加了权重的概念,认为相邻点的距离远近对当前像素点的影响是不同的,距离越近的像素点对应当前像素的影响越大,从而实现图像锐化并突出边缘轮廓。但Sobel算子并不是基于图像灰度进行处理的,因为Sobel算子并没有严格地模拟人的视觉生理特性,因此图像轮廓的提取有时并不能让人满意。当对精度要求不是很高时,Sobel算子是一种较为常用的边缘检测方法。

它的水平和垂直方向的卷积核如下:
在这里插入图片描述
接口说明:

void cv::Sobel(InputArray src,OutputArray dst,int ddepth,int dx,int dy,int ksize = 3,double scale = 1,double delta = 0,int borderType = cv::BORDER_DEFAULT
);

src: 输入图像。可以是单通道(灰度图)或多通道图像。
dst: 输出图像,梯度的计算结果将存储在这里。
ddepth: 输出图像的深度,通常使用 CV_64F 或 CV_32F 表示。
dx: x方向上的导数阶数,设为1表示在水平方向上进行操作。
dy: y方向上的导数阶数,设为1表示在垂直方向上进行操作。
ksize: Sobel核的大小。默认为 3,表示一个 3x3 的核。通常使用奇数值。
scale: 可选的比例因子,用于调整梯度的幅值,也表示对比度。
delta: 可选的偏移值,用于调整输出图像的亮度。
borderType: 边界处理类型,可以使用 cv::BORDER_DEFAULT 或其他合适的边界处理标志。

Sobel算子边缘检测案例:

#include <opencv2/opencv.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>int main() {// 读取图像cv::Mat image = cv::imread("your_image.jpg", cv::IMREAD_GRAYSCALE);if (image.empty()) {std::cerr << "Error: Could not read the image." << std::endl;return -1;}// 应用Sobel算子cv::Mat edges_x, edges_y;cv::Sobel(image, edges_x, CV_64F, 1, 0, 3); // 1表示在水平方向上进行操作cv::Sobel(image, edges_y, CV_64F, 0, 1, 3); // 1表示在垂直方向上进行操作// 计算梯度幅值cv::Mat gradient_magnitude;cv::magnitude(edges_x, edges_y, gradient_magnitude);// 归一化梯度方向到[0, 1]范围cv::normalize(gradient_magnitude, gradient_magnitude, 0, 1, cv::NORM_MINMAX);// 显示结果cv::imshow("Original Image", image);cv::imshow("Sobel Edges X", edges_x);cv::imshow("Sobel Edges Y", edges_y);cv::imshow("Gradient Magnitude", gradient_magnitude);cv::waitKey(0);cv::destroyAllWindows();return 0;
}

在这里插入图片描述

在这里插入图片描述

相关文章:

《opencv实用探索·十一》opencv之Prewitt算子边缘检测,Roberts算子边缘检测和Sobel算子边缘检测

1、前言 边缘检测&#xff1a; 图像边缘检测是指在图像中寻找灰度、颜色、纹理等变化比较剧烈的区域&#xff0c;它们可能代表着物体之间的边界或物体内部的特征。边缘检测是图像处理中的一项基本操作&#xff0c;可以用于人脸识别、物体识别、图像分割等多个领域。 边缘检测…...

prime靶机打靶记录

靶机下载地址 https://download.vulnhub.com/prime/Prime_Series_Level-1.rar nmap搜索目标 使用nmap -sn 192.168.41.0/24找到目标靶机192.168.41.136 扫描端口&#xff0c;因为是靶机&#xff0c;所以速率直接调了10000 扫出来两个端口22和80&#xff0c;进行详细的扫描 没…...

树莓派,linux换清华源

清华源网址 https://mirrors.tuna.tsinghua.edu.cn/help/raspbian/ 更换软件源 鉴于国内网络环境下载各大镜像&#xff0c;软件包速度慢的问题&#xff0c;需要更换软件源&#xff0c;以防下载慢&#xff0c;且在本教程中&#xff0c;统一更换为清华源。 2.3.1 更换树莓派软…...

公有云迁移研究——AWS DMS

大纲 1 什么是DMS2 DMS的作用3 DMS在迁移的时候都做些什么4 在使用DMS的时候我们需要做些什么5 操作5.1 创建两个数据库终端节点5.2 创建迁移任务 6 可能遇到的问题7 总结 在本地机房或其他云往AWS上做迁移时&#xff0c;往往会遇到数据库迁移的任务。如果数据量不是特别大&…...

一起学docker系列之十七Docker Compose 与手动操作的比较与优势分析

目录 1 前言2 不使用 Docker Compose2.1 启动 MySQL 容器2.2 启动 Redis 容器2.3 启动微服务容器 3 使用 Docker Compose4 使用 Docker Compose 的优势5 结语参考地址 1 前言 在当今容器化应用的开发与部署中&#xff0c;容器编排工具的选择对于简化流程、提高效率至关重要。本…...

IP地址定位不准确的情况研究

在互联网的浩瀚海洋中&#xff0c;每一台连接到网络的设备都被赋予了一个独特的标识符&#xff0c;这就是IP地址。它就像是我们在线身份的一部分&#xff0c;帮助我们与他人进行通信&#xff0c;获取信息&#xff0c;以及享受各种网络服务。然而&#xff0c;由于各种原因&#…...

武汉凯迪正大KDZD5289硫化曲线测试仪(电脑无转子硫化仪)

电脑无转子硫化仪 硫化时间测试仪 硫化曲线仪 硫化曲线测试仪 武汉凯迪正大KDZD5289产品概述 KDZD5289硫化曲线测试仪&#xff08;电脑无转子硫化仪&#xff09;采用电脑控制进口温控仪进行准确控温&#xff0c;计算机适时进行数据处理并可进行统计、分析、存储对比等&#xff…...

Topic和Partition

作用 主题作为消息的一级分类, 分区是对二级分类。分区是Kafka可伸缩性和水平扩展的关键, 也是多副本机制保证可用性的基础。分区可以有一到多个副本, 每个副本对应1个日志文件, 每个日志文件对应1到多个日志分段。每个日志分段又可以细分为日志文件, 索引文件和快照文件。 创…...

算法通关村第十四关|黄金挑战|数据流的中位数

数据流的中位数 原题&#xff1a;力扣295. 设计一种数据结构可以支持添加整数和返回中位数的操作。 之前写过找中间用两个堆&#xff0c;这道题就可以使用一个大顶堆和一个小顶堆。 大顶堆存储比较小的元素&#xff0c;小顶堆存储比较大的元素。 class MedianFinder {Prio…...

挑选数据可视化工具:图表类型、交互功能与数据安全

作为一名数据分析师&#xff0c;我经常需要使用各种数据可视化工具来将数据以直观、清晰的方式呈现出来&#xff0c;以便更好地理解和分析。在市面上的众多可视化工具中&#xff0c;我根据实际需求和项目特点进行选择。本文将从以下几个角度对市面上的数据可视化工具进行对比&a…...

华纳云:有效解决服务器宕机的办法

服务器宕机可能是由多种原因引起的&#xff0c;包括硬件故障、软件问题、网络问题等。以下是一些简单的解决服务器宕机问题的办法&#xff1a; 检查硬件连接&#xff1a; 确保服务器的所有硬件连接正常。检查电源线、网络连接、存储设备连接等&#xff0c;确保没有松动或断开的…...

坦克大战-部分

通过键盘操控坦克移动&#xff0c;转弯&#xff0c;射击 消灭所有敌人可以过关 23个类&#xff0c;3个gif图片 wsad控制移动 j射击 砖墙限制移动&#xff0c;可以打穿&#xff1b;铁墙&#xff0c;限制移动&#xff0c;不能打穿&#xff1b;水&#x…...

OracleRac跨网段修改Public IP/VIP/Private IP/Scan IP

本验证于测试环境&#xff0c;生产操作需谨慎 现为测试环境&#xff0c;机器有且仅有两个网卡存在&#xff0c;需求修改Public IP/VIP/Private IP/Scan IP&#xff0c;把Public IP/VIP/Scan IP的网段改为Private IP的网段&#xff0c;Private IP于Public IP网段互换。 先停掉两…...

使用Pytorch从零开始实现BERT

生成式建模知识回顾: [1] 生成式建模概述 [2] Transformer I&#xff0c;Transformer II [3] 变分自编码器 [4] 生成对抗网络&#xff0c;高级生成对抗网络 I&#xff0c;高级生成对抗网络 II [5] 自回归模型 [6] 归一化流模型 [7] 基于能量的模型 [8] 扩散模型 I, 扩散模型 II…...

Python爬虫-新能源汽车销量榜

前言 本文是该专栏的第11篇,后面会持续分享python爬虫案例干货,记得关注。 本文以懂车平台的新能源汽车销量榜单为例,获取各车型的销量排行榜单数据。具体实现思路和详细逻辑,笔者将在正文结合完整代码进行详细介绍。 废话不多说,跟着笔者直接往下看正文详细内容。(附带…...

外包干了8个月,技术退步明显.......

先说一下自己的情况&#xff0c;大专生&#xff0c;18年通过校招进入武汉某软件公司&#xff0c;干了接近4年的功能测试&#xff0c;今年年初&#xff0c;感觉自己不能够在这样下去了&#xff0c;长时间呆在一个舒适的环境会让一个人堕落! 而我已经在一个企业干了四年的功能测…...

<JavaEE> volatile关键字 -- 保证内存可见性、禁止指令重排序

目录 一、内存可见性 1.1 Java内存模型(JMM) 1.2 内存可见性演示 二、指令重排序 三、关键字 volatile 一、内存可见性 1.1 Java内存模型(JMM) 1&#xff09;什么是Java内存模型&#xff08;JMM&#xff09;&#xff1f;Java内存模型即Java Memory Model&#xff0c;简…...

docker安装mysql8

docker安装mysql8 docker search mysql:8 #搜索可以使用的msyql8的镜像 docker pull mysql:8.0.27 #拉去mysql8的镜像 创建挂载的宿主机目录 mkdir -p /data/mysql/mysql8/conf # 配置文件目录 mkdir -p /data/mysql/mysql8/data # 数据目录 touch /data/mysql/mysql8/conf/my.…...

消息丢失排查方法?

遇到丢消息问题&#xff0c;如果是单聊&#xff0c;群聊&#xff0c;聊天室&#xff0c;系统消息可以在开发者后台北极星自助查询一下消息是否发送成功。根据您实际发送的相关信息&#xff08;发送者、接收者、时间、消息 ID ……&#xff09;看是否可以查到消息 如果消息查不到…...

Linux 匿名页反向映射

1. 何为反向映射 正向映射&#xff1a; 用户进程在申请内存时&#xff0c;内核并不会立刻给其分配物理内存&#xff0c;而是先为其分配一段虚拟地址空间&#xff0c;当进程访问该虚拟地址空间时&#xff0c;触发page fault异常&#xff0c;异常处理流程中会为其分配物理页面&am…...

uniapp 对接腾讯云IM群组成员管理(增删改查)

UniApp 实战&#xff1a;腾讯云IM群组成员管理&#xff08;增删改查&#xff09; 一、前言 在社交类App开发中&#xff0c;群组成员管理是核心功能之一。本文将基于UniApp框架&#xff0c;结合腾讯云IM SDK&#xff0c;详细讲解如何实现群组成员的增删改查全流程。 权限校验…...

Linux 文件类型,目录与路径,文件与目录管理

文件类型 后面的字符表示文件类型标志 普通文件&#xff1a;-&#xff08;纯文本文件&#xff0c;二进制文件&#xff0c;数据格式文件&#xff09; 如文本文件、图片、程序文件等。 目录文件&#xff1a;d&#xff08;directory&#xff09; 用来存放其他文件或子目录。 设备…...

Debian系统简介

目录 Debian系统介绍 Debian版本介绍 Debian软件源介绍 软件包管理工具dpkg dpkg核心指令详解 安装软件包 卸载软件包 查询软件包状态 验证软件包完整性 手动处理依赖关系 dpkg vs apt Debian系统介绍 Debian 和 Ubuntu 都是基于 Debian内核 的 Linux 发行版&#xff…...

java调用dll出现unsatisfiedLinkError以及JNA和JNI的区别

UnsatisfiedLinkError 在对接硬件设备中&#xff0c;我们会遇到使用 java 调用 dll文件 的情况&#xff0c;此时大概率出现UnsatisfiedLinkError链接错误&#xff0c;原因可能有如下几种 类名错误包名错误方法名参数错误使用 JNI 协议调用&#xff0c;结果 dll 未实现 JNI 协…...

Cilium动手实验室: 精通之旅---20.Isovalent Enterprise for Cilium: Zero Trust Visibility

Cilium动手实验室: 精通之旅---20.Isovalent Enterprise for Cilium: Zero Trust Visibility 1. 实验室环境1.1 实验室环境1.2 小测试 2. The Endor System2.1 部署应用2.2 检查现有策略 3. Cilium 策略实体3.1 创建 allow-all 网络策略3.2 在 Hubble CLI 中验证网络策略源3.3 …...

MMaDA: Multimodal Large Diffusion Language Models

CODE &#xff1a; https://github.com/Gen-Verse/MMaDA Abstract 我们介绍了一种新型的多模态扩散基础模型MMaDA&#xff0c;它被设计用于在文本推理、多模态理解和文本到图像生成等不同领域实现卓越的性能。该方法的特点是三个关键创新:(i) MMaDA采用统一的扩散架构&#xf…...

tree 树组件大数据卡顿问题优化

问题背景 项目中有用到树组件用来做文件目录&#xff0c;但是由于这个树组件的节点越来越多&#xff0c;导致页面在滚动这个树组件的时候浏览器就很容易卡死。这种问题基本上都是因为dom节点太多&#xff0c;导致的浏览器卡顿&#xff0c;这里很明显就需要用到虚拟列表的技术&…...

智能AI电话机器人系统的识别能力现状与发展水平

一、引言 随着人工智能技术的飞速发展&#xff0c;AI电话机器人系统已经从简单的自动应答工具演变为具备复杂交互能力的智能助手。这类系统结合了语音识别、自然语言处理、情感计算和机器学习等多项前沿技术&#xff0c;在客户服务、营销推广、信息查询等领域发挥着越来越重要…...

MFC 抛体运动模拟:常见问题解决与界面美化

在 MFC 中开发抛体运动模拟程序时,我们常遇到 轨迹残留、无效刷新、视觉单调、物理逻辑瑕疵 等问题。本文将针对这些痛点,详细解析原因并提供解决方案,同时兼顾界面美化,让模拟效果更专业、更高效。 问题一:历史轨迹与小球残影残留 现象 小球运动后,历史位置的 “残影”…...

RabbitMQ入门4.1.0版本(基于java、SpringBoot操作)

RabbitMQ 一、RabbitMQ概述 RabbitMQ RabbitMQ最初由LShift和CohesiveFT于2007年开发&#xff0c;后来由Pivotal Software Inc.&#xff08;现为VMware子公司&#xff09;接管。RabbitMQ 是一个开源的消息代理和队列服务器&#xff0c;用 Erlang 语言编写。广泛应用于各种分布…...