【OpenCV实现平滑图像形态学变化】

文章目录

    • 概要
    • 目标
    • 腐蚀
    • 膨胀
    • 开运算
    • 结构元素(内核)
    • 小结

概要

形态学变化是一组简单的图像操作,主要用于处理二值图像,即只包含黑和白两种颜色的图像。这些操作通常需要两个输入,原始图像和一个内核(kernel),内核的形状和大小决定了操作的性质。

文章将首先介绍腐蚀和膨胀这两个基本的形态学算子。腐蚀操作通过内核在图像上滑动,将像素值置为内核覆盖区域内的最小值,用于消除图像中的小物体或者噪点。相反,膨胀操作将像素值置为内核覆盖区域内的最大值,常用于连接图像中的物体或者填充小的空洞。

随后,文章将介绍其他常见的形态学算子,如开运算和闭运算。开运算是先进行腐蚀操作,再进行膨胀操作,常用于去除噪声和分离物体。闭运算则是先进行膨胀操作,再进行腐蚀操作,常用于填充小洞和连接物体

目标

不同的形态学运算例如腐蚀、膨胀、开运算、闭运算。
不同的函数列如cv.erode()、cv.dilate()、cv.morphologyEx()等等。

腐蚀

是一种基本的形态学操作,其原理类似于自然界中的水土流失现象。在腐蚀操作中,一个内核(kernel)在图像上滑动,如果内核覆盖下的所有像素都为1(即白色,表示前景物体),那么中心像素点就会被赋值为1,否则被腐蚀掉(赋值为0)。

这种操作导致了图像中前景物体的边界被侵蚀,保持前景物体为白色的同时,减小了其厚度或尺寸。换句话说,图像中的白色区域会逐渐减小。腐蚀操作在去除小白点噪声(例如图像中的小杂点)和分离连接在一起的对象等方面非常有效。通过选择合适的内核大小,可以调整腐蚀的程度,使其更加适应不同场景下的图像处理需求。

import cv2 as cv
import numpy as np

# 读取图像
img = cv.imread('img.png', 0)

# 创建一个 5x5 的内核(矩阵)
kernel = np.ones((5, 5), np.uint8)

# 使用腐蚀操作,iterations参数表示腐蚀操作的次数
erosion = cv.erode(img, kernel, iterations=1)

# 显示原始图像
cv.imshow('Original Image', img)

# 显示腐蚀后的图像
cv.imshow('Eroded Image', erosion)

# 等待用户按下任意键后关闭窗口
cv.waitKey(0)
cv.destroyAllWindows()

腐蚀结果:
在这里插入图片描述

膨胀

膨胀是一种形态学操作,与腐蚀相反。它的基本思想是通过内核的滑动,只要内核下的像素中有一个为1,中心像素就会被赋值为1(这类似于逻辑或运算)。膨胀操作会扩大白色物体(或前景物体)的区域或大小。在去除噪声时,通常会先进行腐蚀操作,然后再进行膨胀操作。这是因为腐蚀能够去除小的白色噪声,但同时也可能腐蚀掉我们需要保留的物体。膨胀操作的目的就是扩大物体,使其恢复到原始大小和形状。

在膨胀操作中,噪声已经在腐蚀阶段被去除,因此在膨胀时不会再次引入噪声,但物体的大小和体积会得到恢复。此外,膨胀操作还对有破损或间断连接的物体部分进行恢复,使其更加完整。通过膨胀操作,可以使图像中的白色区域逐渐增大,从而更好地突出物体的特征。

在这里插入图片描述

开运算

开运算只是先腐蚀后膨胀的另一个名称。正如我们上面所解释的,它对于消除噪音很有用。这里我们函数cv.morphologyEx()。

import cv2 as cv
import numpy as np

# 读取图像
img = cv.imread('img.png', 0)

# 创建一个 5x5 的内核(矩阵)
kernel = np.ones((5, 5), np.uint8)

# 使用开运算,先腐蚀后膨胀,可以去除噪声并保持物体的整体形状
opening = cv.morphologyEx(img, cv.MORPH_OPEN, kernel)

# 显示原始图像
cv.imshow('Original Image', img)

# 显示开运算后的图像
cv.imshow('Opened Image', opening)

# 等待用户按下任意键后关闭窗口
cv.waitKey(0)
cv.destroyAllWindows()

在这里插入图片描述

闭运算
闭运算和开运算相反,先膨胀后腐蚀。它对于关闭前景对象内的小孔或对象上的小黑点非常有用。

import cv2 as cv
import numpy as np

# 读取图像
img = cv.imread('img.png', 0)

# 创建一个 5x5 的内核(矩阵)
kernel = np.ones((5, 5), np.uint8)

# 使用闭运算,先膨胀后腐蚀,可以填充前景物体内部的小孔,平滑物体的边界
closing = cv.morphologyEx(img, cv.MORPH_CLOSE, kernel)

# 显示原始图像
cv.imshow('Original Image', img)

# 显示闭运算后的图像
cv.imshow('Closed Image', closing)

# 等待用户按下任意键后关闭窗口
cv.waitKey(0)
cv.destroyAllWindows()

在这里插入图片描述

形态梯度
这是图像的膨胀和腐蚀之间做了一次差
结果将看起来像只留下对象的轮廓。

import cv2 as cv
import numpy as np

# 读取图像
img = cv.imread('img.png', 0)

# 创建一个 5x5 的内核(矩阵)
kernel = np.ones((5, 5), np.uint8)

# 使用形态梯度,通过膨胀和腐蚀的差别,突出物体的边缘
gradient = cv.morphologyEx(img, cv.MORPH_GRADIENT, kernel)

# 显示原始图像
cv.imshow('Original Image', img)

# 显示形态梯度后的图像
cv.imshow('Gradient Image', gradient)

# 等待用户按下任意键后关闭窗口
cv.waitKey(0)
cv.destroyAllWindows()

在这里插入图片描述

顶帽
它是输入图像和开运算图像之间的差。下面的示例是针对 9x9 内核完成的。

import cv2 as cv
import numpy as np

# 读取图像
img = cv.imread('img.png', 0)

# 创建一个 5x5 的内核(矩阵)
kernel = np.ones((5, 5), np.uint8)

tophat = cv.morphologyEx(img, cv.MORPH_TOPHAT, kernel)

# 显示原始图像
cv.imshow('Original Image', img)

# 显示形态梯度后的图像
cv.imshow('Gradient Image', tophat)

# 等待用户按下任意键后关闭窗口
cv.waitKey(0)
cv.destroyAllWindows()

在这里插入图片描述

底帽
它是闭运算图像和输入图像的差

import cv2 as cv
import numpy as np

# 读取图像
img = cv.imread('img.png', 0)

# 创建一个 5x5 的内核(矩阵)
kernel = np.ones((5, 5), np.uint8)

blackhat = cv.morphologyEx(img, cv.MORPH_BLACKHAT, kernel)
# 显示原始图像
cv.imshow('Original Image', img)

# 显示形态梯度后的图像
cv.imshow('Gradient Image', blackhat)

# 等待用户按下任意键后关闭窗口
cv.waitKey(0)
cv.destroyAllWindows()

在这里插入图片描述

结构元素(内核)

在形态学变换中,我们经常需要定义一个内核来指导图像处理。在前面的例子中,我们手动创建了一个矩形内核,但在实际应用中,可能需要不同形状和大小的内核。为了方便地获取这些内核,OpenCV提供了一个函数cv.getStructuringElement()。

使用该函数,您只需要传递内核的形状和大小,就可以获得所需的内核。

cv.getStructuringElement(cv.MORPH_RECT, (5, 5))

如果需要一个椭圆形内核,可以使用以下代码:

cv.getStructuringElement(cv.MORPH_ELLIPSE, (5, 5))

类似地,如果需要一个十字形内核,可以使用

cv.getStructuringElement(cv.MORPH_CROSS, (5, 5))

小结

形态学变换是一种基于图像形状的简单而有效的处理方法,通常应用于二值图像(只包含黑白两种颜色)。在形态学变换中,我们使用内核(也称为结构化元素)来定义操作的性质和形状。

腐蚀是一种形态学变换,它侵蚀了前景物体(白色区域)的边界,通常用于去除小白点噪声或分离连接的对象。使用cv.erode()函数,我们可以将内核滑动在图像上,将内核覆盖下的像素点都为1时,中心像素点就会被赋值为1,其他时候都为0,从而缩小白色区域。

膨胀则与腐蚀相反,它会扩大白色物体的区域,常用于恢复连接对象的大小和形状。使用cv.dilate()函数,内核覆盖下的像素点只需有一个为1,中心像素点就会被赋值为1,从而扩大白色区域。

开运算是先腐蚀后膨胀的组合操作,它可以去除噪声并保持物体的整体形状。闭运算则是先膨胀后腐蚀的组合操作,它可以填充前景物体内部的小孔,平滑物体的边界。这两种操作分别使用cv.morphologyEx()函数中的cv.MORPH_OPEN和cv.MORPH_CLOSE参数实现。

为了方便地定义不同形状和大小的内核,OpenCV提供了cv.getStructuringElement()函数。通过传递内核的形状和大小参数,可以获得所需的内核。矩形、椭圆和十字形内核是常见的选择,可以根据具体任务的要求灵活选择合适的内核形状。

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

第11期 | GPTSecurity周报

GPTSecurity是一个涵盖了前沿学术研究和实践经验分享的社区,集成了生成预训练 Transformer(GPT)、人工智能生成内容(AIGC)以及大型语言模型(LLM)等安全领域应用的知识。在这里,您可以…

CloudQuery + StarRocks:打造高效、安全的数据库管控新模式

随着技术的迅速发展,各种多元化的数据库产品应运而生,它们不仅类型众多,而且形式各异,国产化数据库千余套,开源数据库百余套 OceanBase 、PolarDB 、StarRocks…还有一些像 Oracle、MySQL 这些传统数据库。这些数据库产…

flutter开发实战-hero实现图片预览功能extend_image

flutter开发实战-hero实现图片预览功能extend_image 在开发中,经常遇到需要图片预览,当feed中点击一个图片,开启预览,多个图片可以左右切换swiper,双击图片及手势进行缩放功能。 这个主要实现使用extend_image插件。在…

达梦:开启sql日志记录

前言 开启sql日志记录,可协助排查定位数据库问题。生产开启会有一定的性能消耗,建议打开 SQL 日志异步刷盘功能 1.配置sqllog.ini文件 sqllog.ini 用于 SQL 日志的配置,当且仅当 INI 参数 SVR_LOG1 时使用。 运行中的数据库实例,可…

Go学习第十一章——协程goroutine与管道channel

Go协程goroutine与管道channel 1 协程goroutine1.1 基本介绍1.2 快速入门1.3 调度模型:MPG模式介绍1.4 设置cpu数1.5 协程资源竞争问题1.6 解决协程并发方案 2 管道channel2.1 基本介绍2.2 快速入门2.3 管道的关闭和遍历2.4 管道和协程的结合2.5 声明 只读/只写 的管…

GZ035 5G组网与运维赛题第2套

2023年全国职业院校技能大赛 GZ035 5G组网与运维赛项(高职组) 赛题第2套 一、竞赛须知 1.竞赛内容分布 竞赛模块1--5G公共网络规划部署与开通(35分) 子任务1:5G公共网络部署与调试(15分) 子任务2:5G室内与室外站点建设(20分) 竞赛模块2--5G公共网络运维与优化(…

Codeforces Round 905 (Div. 3)ABCDEF

Codeforces Round 905 (Div. 3) 目录 A. Morning题意思路核心代码 B. Chemistry题意思路核心代码 C. Raspberries题意思路核心代码 D. In Love题意思路核心代码 E. Look Back题意思路核心代码 A. Morning 题意 从一开始,每一次操作可以选择当前的数字打印或者是移…

Vue3 + Tsx 集成 ace-editor编辑器

Ace Editor介绍 Ace Editor(全名:Ajax.org Cloud9 Editor)是一个开源的代码编辑器,旨在提供强大的代码编辑功能,通常用于构建基于Web的代码编辑应用程序。它最初由Cloud9 IDE开发,现在由开源社区维护。 主…

C++ 左值、右值、左值引用以及右值引用

一、左值和右值 将亡值 1.左值 左值是一个表示数据的表达式,比如:变量名、解引用的指针变量。一般地,我们可以获取它的地址和对它赋值,但被 const 修饰后的左值(常性),不能给它赋值&#xff0…

【安装tensorflow-CPU版本】

一、安装目的二、安装过程三、总结 一、安装目的 使自己的jupyter能用tensorflow 二、安装过程 首先打开anaconda prompt 接着输入conda list 查看自己是否安装了tensorflow 在 Python 中使用 pip 工具来升级 pip 自身并指定了使用清华大学的镜像源进行安装 python -m pip …

手写Vue渲染器render函数

使用js对象来描述UI更加的灵活。“这种对象”在vue框架中被称为虚拟DOM,渲染函数内部可以创建虚拟DOM,然后vue.js可以将其内容进行渲染。 1.渲染器的介绍 渲染器的作用就是把虚拟DOM渲染为真实DOM 思考下,我们有一个虚拟 DOM,如…

K8s概念汇总-笔记

目录 1.Master 1.1在Master上运⾏着以下关键进程 2.什么是Node? 1.2在每个Node上都运⾏着以下关键进程 3.什么是 Pod ? 4. 什么是Label ? 5.Replication Controller 6.Deployment 6.1Deployment的典型场景: 7.Horizontal Pod Autoscaler TODO…

【计算机毕设小程序案例】基于SpringBoot的小演员招募小程序

前言:我是IT源码社,从事计算机开发行业数年,专注Java领域,专业提供程序设计开发、源码分享、技术指导讲解、定制和毕业设计服务 👉IT源码社-SpringBoot优质案例推荐👈 👉IT源码社-小程序优质案例…

Linux mkdir命令:创建目录(文件夹)

mkdir 命令,是 make directories 的缩写,用于创建新目录,此命令所有用户都可以使用。mkdir 命令的基本格式为: [rootlocalhost ~]# mkdir [-mp] 目录名 -m 选项用于手动配置所创建目录的权限,而不再使用默认权限。 -p…

[ubuntu系统下的文本编辑器nano,vim,gedit,文件使用,以及版本更新问题]

文本编辑器概要 在Ubuntu系统下,有许多文本编辑器可供选择,每个编辑器都有其独特的特性和用途。以下是一些常见的文本编辑器: Gedit: 这是Ubuntu默认的文本编辑器,它简单易用,适合基本的文本编辑任务。 安…

银河麒麟v10x86或者arm离线安装服务

银河麒麟v10x86或者arm离线安装服务 最近有个项目,甲方的服务器用的全是国产化服务器银河麒麟,架构是x86的然后也无法连接外网,需要离线安装服务正常思路就是找到离线安装的包,然后拷贝到现场的服务器中进行安装所以问题就在于如…

墨西哥专线相关问题快问快答

随着全球贸易的不断发展,越来越多的企业在寻求更便捷、高效的物流解决方案。墨西哥专线作为一种跨境物流方式,受到了越来越多企业的关注。本文将为您解答关于墨西哥专线的相关问题,帮助您更好地了解和运用这一物流方式。 一、墨西哥专线是什么…

Prompt设计与大语言模型微调

本文主要介绍了Prompt设计、大语言模型SFT和LLM在手机天猫AI导购助理项目应用。 ChatGPT基本原理 “会说话的AI”,“智能体” 简单概括成以下几个步骤: 预处理文本:ChatGPT的输入文本需要进行预处理。输入编码:ChatGPT将经过预处理…

MySQL 概述 数据库表操作 数据增删改

目录 MySQL概述前言安装与配置MySQL登录与卸载 数据模型概述SQL简介SQL通用语法简介SQL分类 数据库设计(数据库操作)-DDL数据库操作查询数据库 show databases、select database()创建数据库 create database使用数据库 use删除数据库 drop database 图形化工具连接数据库操作数…

zk-Bench:SNARKs性能对比评估工具

1. 引言 JENS ERNSTBERGER等人2023年论文《zk-Bench: A Toolset for Comparative Evaluation and Performance Benchmarking of SNARKs》。 zk-Bench,定位为: 定位为首个公钥密码学性能评估基准测试框架和工具,重点关注通用ZKP系统的实测评…