EmguCV学习笔记 VB.Net 4.4 图像形态学

embedded/2024/10/15 19:12:26/

  版权声明:本文为博主原创文章,转载请在显著位置标明本文出处以及作者网名,未经作者允许不得用于商业目的。

教程VB.net版本请访问:
EmguCV学习笔记 VB.Net 目录-CSDN博客

教程C#版本请访问:EmguCV学习笔记 C# 目录-CSDN博客

笔者的博客网址:https://blog.csdn.net/uruseibest

教程配套文件及相关说明以及如何获得pdf教程和代码(博客上的教程内容会和pdf教程一致,教程中也会包含所有代码),请移步:EmguCV学习笔记

 

4.4 图像形态学

图像形态学是数字图像处理中的一种重要技术,它主要用于对二值图像进行分析和处理。图像形态学可以用于图像去噪、边缘检测、形态分析等方面。EmguCV提供了一系列的图像形态学操作函数,包括膨胀、腐蚀、开运算、闭运算等。

1. 膨胀 (Dilation)

膨胀是一种形态学操作,其基本思想是用一个结构元素 (Structuring Element) 在图像上滑动,将结构元素包含的像素值中的最大值作为当前像素值,从而实现对图像边缘的扩张和增强。EmguCV中的膨胀函数为CvInvoke.Dilate。

2. 腐蚀 (Erosion)

腐蚀是一种形态学操作,其基本思想是用一个结构元素在图像上滑动,将结构元素包含的像素值中的最小值作为当前像素值,从而实现对图像边缘的收缩和平滑。EmguCV中的腐蚀函数为CvInvoke.Erode。

3. 开运算 (Opening)

开运算是一种形态学操作,其基本思想是先进行一次腐蚀操作,再进行一次膨胀操作,从而可以去除比较小的物体、断开细长的物体等。EmguCV中的开运算函数为CvInvoke.MorphologyEx,其类型为MorphOp.Open。

4. 闭运算 (Closing)

闭运算是一种形态学操作,其基本思想是先进行一次膨胀操作,再进行一次腐蚀操作,从而可以填充物体内的小孔、连接断开的物体等。EmguCV中的闭运算函数为CvInvoke.MorphologyEx,其类型为MorphOp.Close。

图像形态学操作需要根据图像的特点和处理目的进行合理的选择和组合,才能达到良好的效果。

注意:图像形态学针对的是非黑色部分(非0部分)操作。

4.4.1 GetStructuringElement

通过CvInvoke.GetStructuringElement方法可以创建形态学操作的结构元素。该方法返回一个Mat对象。定义如下:

Public Shared Function GetStructuringElement(shape As Emgu.CV.CvEnum.ElementShape, ksize As System.Drawing.Size, anchor As System.Drawing.Point) As Emgu.CV.Mat

参数说明:

  1. shape:结构元素的形状,可以是Rectangle(矩形)、Cross(十字形)、Ellipse(椭圆形)。
  2. size:结构元素的大小。
  3. anchor:结构元素的锚点位置,用Point结构指定。可以使用 Nothing 或者(-1,-1),表示将锚点放置在结构元素的中心。

下面的代码创建了一个3x3的十字形结构元素:

Dim element As Mat

element= CvInvoke.GetStructuringElement(ElementShape.Cross, New Size(3, 3))

4.4.2 Erode

Erode方法对图像进行腐蚀操作,该方法声明如下:

Public Shared Sub Erode(src As Emgu.CV.IInputArray, dst As Emgu.CV.IOutputArray, element As Emgu.CV.IInputArray, anchor As System.Drawing.Point, iterations As Integer, borderType As Emgu.CV.CvEnum.BorderType, borderValue As Emgu.CV.Structure.MCvScalar)

参数说明:

  1. element:结构元素。
  2. anchor:结构元素的锚点位置,类型为Point。指定结构元素的锚点位置,一般为结构元素的中心,即(-1,-1)。
  3. iterations:腐蚀操作的迭代次数,类型为Integer。默认为1,表示进行一次腐蚀操作。
  4. Iterations:操作的迭代次数,类型为Integer。默认为1,表示进行一次膨胀操作。
  5. borderType:边界处理方式,类型为BorderType(详见4.2.1节【BorderType】)。需要注意的是,使用的BorderType类型不同生成结果不同。
  6. borderValue:边界值,类型为MCvScalar。当borderType为BorderType.Constant时,可以指定边界的像素值。通常设置为Nothing。

【代码位置:frmChapter4】Button12_Click、printMatByte

    'Erode腐蚀

    Private Sub Button12_Click(sender As Object, e As EventArgs) Handles Button12.Click

        '创建结构元素,这里是一个3*3大小的十字形结构

        Dim kernel As New Mat

        kernel = CvInvoke.GetStructuringElement(ElementShape.Cross, New Drawing.Size(3, 3), New Point(-1, -1))

        Dim bte1(,) As Byte

        bte1 = {

            {0, 1, 1, 1, 1, 0, 0, 0, 0},

            {1, 1, 1, 1, 1, 1, 1, 1, 0},

            {1, 1, 1, 1, 1, 1, 1, 1, 0},

            {1, 1, 1, 1, 1, 1, 1, 1, 0},

            {0, 1, 1, 1, 1, 1, 1, 1, 0},

            {0, 1, 1, 1, 1, 1, 1, 1, 1},

            {0, 1, 1, 1, 1, 1, 1, 1, 1},

            {0, 1, 1, 1, 1, 1, 1, 1, 1},

            {0, 0, 0, 0, 1, 1, 1, 1, 0}

        }

        Dim matr1 As New Matrix(Of Byte)(bte1)

        Dim m1 As New Mat

        m1 = matr1.Mat

        Dim merode As New Mat        '

        '这里使用了2次迭代

        CvInvoke.Erode(m1, merode, kernel, New Point(-1, -1), 2, BorderType.Constant, Nothing)

        Call printMatByte(merode)

    End Sub

    '输出Mat的值

    Private Sub printMatByte(ByVal m As Mat)

        Dim matr As New Matrix(Of Byte)(m.Rows, m.Cols, m.NumberOfChannels)

        m.CopyTo(matr)

        For i As Integer = 0 To matr.Rows - 1

            For j As Integer = 0 To matr.Cols - 1

                Console.Write(matr(i, j))

                If j <> matr.Cols - 1 Then

                    Console.Write(",")

                End If

            Next

            Console.WriteLine()

        Next

End Sub

下图演示了使用腐蚀进行2次迭代的结果:

图4-12 进行二次腐蚀的情况

4.4.3 Dilate

Dilate方法对图像进行膨胀操作,该方法声明如下:

Public Shared Sub Dilate(src As Emgu.CV.IInputArray, dst As Emgu.CV.IOutputArray, element As Emgu.CV.IInputArray, anchor As System.Drawing.Point, iterations As Integer, borderType As Emgu.CV.CvEnum.BorderType, borderValue As Emgu.CV.Structure.MCvScalar)

参数请参看4.3.2节【Erode】中的介绍。

【代码位置:frmChapter4】Button13_Click

    'Dilate 膨胀

    Private Sub Button13_Click(sender As Object, e As EventArgs) Handles Button13.Click

        '创建结构元素,这里是一个3*3大小的十字形结构

        Dim kernel As New Mat

        kernel = CvInvoke.GetStructuringElement(ElementShape.Cross, New Drawing.Size(3, 3), New Point(-1, -1))

        Dim bte2(,) As Byte

        bte2 = {

            {0, 0, 0, 0, 0, 0, 0, 0, 0},

            {0, 0, 0, 0, 0, 0, 0, 0, 0},

            {0, 0, 1, 1, 1, 0, 0, 0, 0},

            {0, 0, 1, 1, 1, 0, 0, 0, 0},

            {0, 0, 0, 1, 1, 0, 0, 0, 0},

            {0, 0, 0, 0, 1, 1, 1, 0, 0},

            {0, 0, 0, 0, 1, 1, 1, 0, 0},

            {0, 0, 0, 0, 0, 0, 0, 0, 0},

            {0, 0, 0, 0, 0, 0, 0, 0, 0}

        }

        Dim matr2 As New Matrix(Of Byte)(bte2)

        Dim m2 As New Mat

        m2 = matr2.Mat

        Dim mdilate As New Mat

        '这里使用了2次迭代进行膨胀

        CvInvoke.Dilate(m2, mdilate, kernel, New Point(-1, -1), 2, BorderType.Constant, Nothing)

        Call printMatByte(mdilate)

End Sub

下图演示了使用腐蚀进行2次迭代的结果:

 

图4-13 进行二次膨胀的情况

以下代码演示了使用腐蚀和膨胀来处理图像

【代码位置:frmChapter4】Button14_Click

    'ErodeDilate

    Private Sub Button14_Click(sender As Object, e As EventArgs) Handles Button14.Click

        Dim m As Mat = CvInvoke.Imread("C:\lessons\lena.jpg", CvEnum.ImreadModes.Color)

        ImageBox1.Image = m

        Dim mElement As New Mat

        mElement = CvInvoke.GetStructuringElement(ElementShape.Cross, New Drawing.Size(3, 3), New Point(-1, -1))

        '腐蚀

        Dim mout1 As New Mat

        CvInvoke.Erode(m, mout1, mElement, New Point(-1, -1), 2, BorderType.Default, Nothing)

        ImageBox2.Image = mout1

        '膨胀

        Dim mout2 As New Mat

        CvInvoke.Dilate(m, mout2, mElement, New Point(-1, -1), 2, BorderType.Default, Nothing

        ImageBox3.Image = mout2

End Sub

运行后如下图所示:

 

图4-14 使用腐蚀和膨胀处理图像

4.4.4 MorphologyEx

为了实现更多图像形态学操作,EmguCV提供了CvInvoke.MorphologyEx方法,声明如下:

Public Shared Sub MorphologyEx(src As Emgu.CV.IInputArray, dst As Emgu.CV.IOutputArray, operation As Emgu.CV.CvEnum.MorphOp, kernel As Emgu.CV.IInputArray, anchor As System.Drawing.Point, iterations As Integer, borderType As Emgu.CV.CvEnum.BorderType, borderValue As Emgu.CV.Structure.MCvScalar)

参数说明,其余参数请参看4.3.2节【Erode】中的介绍:

  1. operation:形态学操作类型,类型为MorphOp,包括以下几种形态学操作:
    1. Dilate:膨胀操作,
    2. Erode:腐蚀操作。
    3. Open:开运算,先进行腐蚀再进行膨胀,可以用于去除小的噪点和连接断开的区域。
    4. Close:闭运算,先进行膨胀再进行腐蚀,可以用于填充小的空洞和分离连接的区域。
    5. Gradient:梯度运算,用膨胀图像减去腐蚀图像,可以得到图像边缘。
    6. TopHat:高帽运算,用原始图像减去开运算后的图像,可以提取图像中的亮点或小的细节信息。
    7. BlackHat:低帽运算,用闭运算后的图像减去原始图像,可以提取图像中的暗点或背景信息。
    8. HitMiss:击中击不中运算,用于确定图像中是否存在指定的形状。它需要两个结构元素:一个前景结构元素和一个背景结构元素。在输入图像上,如果前景结构元素可以同时与前景像素和背景像素匹配,那么该像素属于击中集合;否则,它属于击不中集合。通过对击中集合进行膨胀操作并减去原始击中集合得到最终结果。

以下代码演示了使用开运算来处理图像数据,同时与腐蚀,膨胀操作图像数据做对比。

【代码位置:frmChapter4】Button15_Click

   'MorphologyEx:开运算:先腐蚀,再膨胀

    Private Sub Button15_Click(sender As Object, e As EventArgs) Handles Button15.Click

        Dim bte(,) As Byte

        bte = {

            {0, 0, 0, 0, 0, 0, 0, 0, 0},

            {0, 1, 0, 0, 0, 0, 0, 0, 0},

            {1, 1, 1, 0, 0, 0, 1, 1, 1},

            {1, 1, 1, 1, 1, 1, 1, 1, 1},

            {1, 1, 1, 1, 1, 1, 1, 1, 1},

            {1, 1, 1, 0, 0, 0, 1, 1, 1},

            {1, 1, 1, 1, 1, 1, 1, 1, 1},

            {0, 1, 0, 0, 0, 0, 1, 0, 0},

            {0, 0, 0, 0, 0, 0, 0, 0, 0}

        }

        Dim matr As New Matrix(Of Byte)(bte)

        Dim m As New Mat

        m = matr.Mat

        '创建结构元素,这里是一个3*3大小的十字形结构

        Dim kernel As New Mat

        kernel = CvInvoke.GetStructuringElement(ElementShape.Cross, New Drawing.Size(3, 3), New Point(-1, -1))

        '进行开运算

        Dim mMorphology As New Mat

        CvInvoke.MorphologyEx(m, mMorphology, MorphOp.Open, kernel, New Point(-1, -1), 1, BorderType.Constant, Nothing)

        Call printMatByte(mMorphology)

        Console.WriteLine("===============================")

        '先腐蚀

        Dim merode As New Mat

        CvInvoke.Erode(m, merode, kernel, New Point(-1, -1), 1, BorderType.Constant, Nothing)

        Call printMatByte(merode)

        Console.WriteLine("===============================")

        '再膨胀

        Dim mdilate As New Mat

        CvInvoke.Dilate(merode, mdilate, kernel, New Point(-1, -1), 1, BorderType.Constant, Nothing)

        Call printMatByte(mdilate)

End Sub

下图演示了使用开运算处理图像数据的结果:

 

图4-15 开运算处理图像数据

以下代码演示了使用闭运算来处理图像数据,同时与膨胀,腐蚀操作图像数据做对比。

【代码位置:frmChapter4】Button16_Click

   'MorphologyEx:闭运算:先膨胀,再腐蚀

    Private Sub Button16_Click(sender As Object, e As EventArgs) Handles Button16.Click

        Dim bte(,) As Byte

        bte = {

            {0, 0, 0, 0, 0, 0, 0, 0, 0},

            {0, 0, 0, 0, 0, 0, 0, 0, 0},

            {0, 1, 1, 1, 0, 1, 1, 1, 0},

            {0, 1, 1, 1, 0, 1, 1, 1, 0},

            {0, 1, 1, 1, 1, 1, 1, 1, 0},

            {0, 1, 1, 1, 0, 1, 1, 1, 0},

            {0, 0, 0, 1, 1, 1, 0, 0, 0},

            {0, 0, 0, 1, 1, 0, 0, 0, 0},

            {0, 0, 0, 0, 0, 0, 0, 0, 0}

        }

        Dim matr As New Matrix(Of Byte)(bte)

        Dim m As New Mat

        m = matr.Mat

        '创建结构元素,这里是一个3*3大小的十字形结构

        Dim kernel As New Mat

        kernel = CvInvoke.GetStructuringElement(ElementShape.Cross, New Drawing.Size(3, 3), New Point(-1, -1))

        '闭运算

        Dim mMorphology As New Mat

        CvInvoke.MorphologyEx(m, mMorphology, MorphOp.Close, kernel, New Point(-1, -1), 1, BorderType.Constant, Nothing)

        Call printMatByte(mMorphology)

        Console.WriteLine("===============================")

        '先膨胀

        Dim mdilate As New Mat

        CvInvoke.Dilate(m, mdilate, kernel, New Point(-1, -1), 1, BorderType.Constant, Nothing)

        Call printMatByte(mdilate)

        Console.WriteLine("===============================")

        '再腐蚀

        Dim merode As New Mat

        CvInvoke.Erode(mdilate, merode, kernel, New Point(-1, -1), 1, BorderType.Constant, Nothing)

        Call printMatByte(merode)

End Sub

下图演示了使用闭运算处理图像数据的结果:

 

图4-16 闭运算处理图像数据

以下代码演示了使用闭运算和开运算来处理图像

【代码位置:frmChapter4】Button17_Click

    'MorphologyEx:开运算和闭运算处理图像

    Private Sub Button17_Click(sender As Object, e As EventArgs) Handles Button17.Click

        Dim m As Mat = CvInvoke.Imread("C:\lessons\lena.jpg", CvEnum.ImreadModes.Color)

        ImageBox1.Image = m

        Dim mElement As New Mat

        mElement = CvInvoke.GetStructuringElement(ElementShape.Cross, New Drawing.Size(3, 3), New Point(-1, -1))

        '开运算

        Dim mout1 As New Mat

        CvInvoke.MorphologyEx(m, mout1, MorphOp.Open, mElement, New Point(-1, -1), 3, BorderType.Default, New MCvScalar(0, 0, 0))

        ImageBox2.Image = mout1

        '闭运算

        Dim mout2 As New Mat

        CvInvoke.MorphologyEx(m, mout2, MorphOp.Close, mElement, New Point(-1, -1), 3, BorderType.Default, New MCvScalar(0, 0, 0))

        ImageBox3.Image = mout2

End Sub

运行后如下图所示:

 

图4-17 开运算和闭运算处理图像


http://www.ppmy.cn/embedded/98693.html

相关文章

数学建模算法总结

数学建模常见算法总结 评价决策类模型 层次分析法 层次分析法根据问题的性质和要达到的总目的&#xff0c;将问题分解为不同的组成因素&#xff0c;并按照因素间的相互关联影响以及隶属关系将因素按不同层次聚集组合&#xff0c;形成一个多层次的分析结构模型&#xff0c;从…

SpringBoot整合MongoDB

目录 什么是MongoDB&#xff1f;Spring Boot整合MongoDB使用MongoDB1.新增文档2.修改文档3.删除文档4.查询文档5.创建索引 什么是MongoDB&#xff1f; MongoDB是一种开源的 分布式文档型数据库管理系统 &#xff0c;它使用类似于JSON的BSON格式&#xff08;Binary JSON&#x…

C++ 设计模式——策略模式

策略模式 策略模式主要组成部分例一&#xff1a;逐步重构并引入策略模式第一步&#xff1a;初始实现第二步&#xff1a;提取共性并实现策略接口第三步&#xff1a;实现具体策略类第四步&#xff1a;实现上下文类策略模式 UML 图策略模式的 UML 图解析 例二&#xff1a;逐步重构…

【区块链+金融服务】“吉惠通”一站式金融综合服务平台 | FISCO BCOS应用案例

释放数据要素价值&#xff0c;FISCO BCOS 2024 应用案例征集 核心企业拥有良好的企业信誉&#xff0c;但有时会由于无可传递的信任背书&#xff0c;而无法为其他环节供应商提供融资支持&#xff0c;无 法促进产业链条良性发展&#xff1b;金融机构难以得到有议价空间的、弹性的…

Apache Flink细粒度资源管理原理

粗粒度资源管理 Apache Flink 1.1.4版本之前使用的是粗粒度的资源管理&#xff0c;即每个算子Slot Request所需要的资源都是未知的&#xff0c;Flink内部用UNKNOWN的特殊值来表示&#xff0c;这个值可以和任意资源规则的物理Slot匹配&#xff0c;站在Taskmanager的角度&#x…

MySQL键分区分区表

什么是键分区分区表&#xff1f; 键分区是一种MySQL数据库中的分区策略&#xff0c;它基于某个列的键值将数据分割成不同的分区。每个键值都会被映射到一个唯一的分区&#xff0c;这样可以确保数据在不同分区中均匀分布。键分区广泛应用于MySQL Cluster环境中&#xff0c;它可…

Ruby模板引擎:构建动态视图的艺术

标题&#xff1a;Ruby模板引擎&#xff1a;构建动态视图的艺术 在Ruby on Rails的世界里&#xff0c;模板引擎是构建动态网页的基石。它们允许开发者将服务器端的逻辑嵌入到HTML中&#xff0c;实现数据的动态展示。本文将深入探讨Ruby中几种常用的模板引擎&#xff0c;包括ERB…

JAVA_7

JAVA_7 JAVA面向对象编程1. 抽象方法和抽象类 JAVA面向对象编程 1. 抽象方法和抽象类 使用abstract修饰的方法&#xff0c;没有方法体&#xff0c;只有声明。定义的是一种“规范”&#xff0c;就是告诉子类必须要给抽象方法提供具体的实现。包含抽象方法的类就是抽象类。通过…