7:OpenCV—图像形态学处理

OpenCV的形态学操作(对象图像进行处理)

包括图像的**腐蚀**、**膨胀**、**开**、**闭**、**形态学梯度、顶帽、黑帽、分支主题、结构元素**等操作。

1.1、膨胀

用3×3的核去扫描二值图像,当核与图像中的前景像素(值为1的像素)有**交集**时,则将二值图像中对应的卷积核中心位置的像素值置为1。

拓展:卷积核可以**为任意形状(除1×1)**,且重置点可以选用卷积核中的**任意位置**,有'**交集'**就对重置点位置像素置1。

1.2、腐蚀

​ 用3×3的核去扫描二值图像,仅当核的与前景像素有**完全重合区域**时,将二值图像中对应的卷积核中心位置的像素保留,其余情况下,将中心位置的像素置0。

​ 拓展:卷积核可以**为任意形状**,且**重置点**可以选用卷积核中的**任意位置。**

**膨胀与腐蚀的区别:**膨胀只要**有交集就触发**,而腐蚀**必须是重置点与前景像素有完全重合区域才保留**。

1.3、开与闭

​ **开:**腐蚀再膨胀,去除微小干扰块。

**闭:**膨胀再腐蚀,填充闭合区域。

1.4、形态学梯度

​ 内梯度:原图 - 腐蚀图

​ 外梯度:膨胀图 - 原图

​ 这里opencv只能直接实现基本梯度,在使用API:morphologyEx 时,调用MORPH_GRADIENT方法即可。

​ 内梯度、外梯度没有直接的API,一般通过已有API间接实现。

1.5、其余形态学操作

**顶帽:**原图 - 开操作后的图

**黑帽:**闭操作后的图 - 原图

**注:**顶帽和黑帽操作用于**获取图像**中的**微小细节**。

击中击不中: 通过特定模板,仅当输入的图像中,**有与模板一模一样的块**时,被击中的输入图像区域才会被保留。

使用API:**morphologyEx** 时,分别调用M**ORPH_TOPHAT 、MORPH_BLACKHAT、MORPH_HITMISS**方法即可实现。

void cv::morphologyEx(InputArray src,

OutputArray dst,

int op,

InputArray kernel,

Point anchor = Point(-1,-1),

int iterations = 1,

int borderType = BORDER_CONSTANT,

const Scalar & borderValue = morphologyDefaultBorderValue()

)

  • src:输入图像,图像的通道数可以是任意的,但是图像的数据类型必须是CV_8U,CV_16U,CV_16S,CV_32F或CV_64F之一。
  • dst:形态学操作后的输出图像,与输入图像具有相同的尺寸和数据类型。
  • op:形态学操作类型的标志,可以选择的标志及含义在表6-6中给出。
  • kernel:结构元素,可以自己生成,也可以用getStructuringElement()函数生成。
  • anchor:中心点在结构元素中的位置,默认参数为结构元素的几何中心点
  • iterations:处理的次数
  • borderType:像素外推法选择标志,取值范围在表3-5中给出。默认参数为BORDER_DEFAULT,表示不包含边界值倒序填充。
  • borderValue:使用边界不变外推法时的边界值。

该函数根据结构元素对输入图像进行多种形态学操作,在处理多通道图像时每个通道独立进行处理。

函数的第一个参数为待形态学处理的图像,图像通道数可以是任意的,但是图像的数据类型必须是CV_8U,CV_16U,CV_16S,CV_32F或CV_64F之一。

函数第二个参数为形态学处理后的输出图像,与输入图像具有相同的尺寸和数据类型。

函数第三个参数是形态学操作类型的选择标志,可以选择的形态学操作类型有开运算、闭运算、形态学梯度、顶帽运算、黑帽运算以及击中击不中变换,详细的参数在表6-6给出。

函数第四个和第五个参数都是与结构元素相关的参数,第四个参数为结构元素,使用的结构元素尺寸越大效果越明显,第四个参数为结构元素的中心位置,第五个参数的默认值为Point(-1,-1),表示结构元素的几何中心处为结构元素的中心点。

函数第六个参数是使用结构元素处理的次数,处理次数越多效果越明显。

函数第七个参数是图像像素外推法的选择标志,

第八个参数为使用边界不变外推法时的边界值,这两个参数对图像中主要部分的形态学操作没有影响,因此在多数情况下使用默认值即可。

测试代码

复制代码
#include <iostream>
#include <opencv2/opencv.hpp>
#include <QDebug>

using namespace cv;
using namespace std;

int main()
{
    //用于验证形态学应用的二值化矩阵
    Mat src = (Mat_<uchar>(9, 12) << 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
    0, 255, 255, 255, 255, 255, 255, 255, 0, 0, 255, 0,
    0, 255, 255, 255, 255, 255, 255, 255, 0, 0, 0, 0,
    0, 255, 255, 255, 255, 255, 255, 255, 0, 0, 0, 0,
    0, 255, 255, 255, 0, 255, 255, 255, 0, 0, 0, 0,
    0, 255, 255, 255, 255, 255, 255, 255, 0, 0, 0, 0,
    0, 255, 255, 255, 255, 255, 255, 255, 0, 0, 255, 0,
    0, 255, 255, 255, 255, 255, 255, 255, 0, 0, 0, 0,
    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
    namedWindow("src", WINDOW_NORMAL);  //可以自由调节显示图像的尺寸
    imshow("src", src);
    // 创建3X3矩形核元素
    Mat kernel = getStructuringElement(0, Size(3,3));

    // 对象矩阵进行膨胀操作
    Mat dilateImg;
    morphologyEx(src, dilateImg, MORPH_DILATE, kernel);
    namedWindow("dilateWd", WINDOW_NORMAL);  //可以自由调节显示图像的尺寸
    imshow("dilateWd", dilateImg);

    // 对象矩阵进行腐蚀操作
    Mat erodeImg;
    morphologyEx(src, erodeImg, MORPH_ERODE, kernel);
    namedWindow("erodeWd", WINDOW_NORMAL);  //可以自由调节显示图像的尺寸
    imshow("erodeWd", erodeImg);

    // 对象矩阵进行开操作
    Mat openImg;
    morphologyEx(src, openImg, MORPH_OPEN, kernel);
    namedWindow("openWd", WINDOW_NORMAL);  //可以自由调节显示图像的尺寸
    imshow("openWd", openImg);

    // 对象矩阵进行闭操作
    Mat closeImg;
    morphologyEx(src, closeImg, MORPH_CLOSE, kernel);
    namedWindow("closeWd", WINDOW_NORMAL);  //可以自由调节显示图像的尺寸
    imshow("closeWd", closeImg);

    // 对象矩阵进行开操作
    Mat topHatImg;
    morphologyEx(src, topHatImg, MORPH_TOPHAT, kernel);
    namedWindow("topHatWd", WINDOW_NORMAL);  //可以自由调节显示图像的尺寸
    imshow("topHatWd", topHatImg);

    // 对象矩阵进行闭操作
    Mat blackImg;
    morphologyEx(src, blackImg, MORPH_BLACKHAT, kernel);
    namedWindow("blackWd", WINDOW_NORMAL);  //可以自由调节显示图像的尺寸
    imshow("blackWd", blackImg);

    // 对象矩阵进行梯度运算操作
    Mat gradientImg;
    morphologyEx(src, gradientImg, MORPH_GRADIENT, kernel);
    namedWindow("gradientWd", WINDOW_NORMAL);  //可以自由调节显示图像的尺寸
    imshow("gradientWd", gradientImg);

    waitKey(0);

    return 0;
}
相关推荐
舒一笑15 分钟前
基础RAG实现,最佳入门选择(六)
人工智能
2401_8582861119 分钟前
CD45.【C++ Dev】STL库的list的使用
开发语言·数据结构·c++·list
SLAM必须dunk38 分钟前
DL___线性神经网络
人工智能·深度学习·神经网络
甜辣uu1 小时前
第七届人工智能技术与应用国际学术会议
人工智能·ei会议·中文核心·国际学术会议
艾立泰智能包装1 小时前
艾立泰智能物流载具管理方案
大数据·人工智能
舒一笑1 小时前
基础RAG实现,最佳入门选择(五)
人工智能
爱看科技1 小时前
谷歌Gemini 2.5全系领跑AI赛道,微美全息加码构建AI+多模态交互生态新范式
人工智能
love530love1 小时前
Python 开发环境全栈隔离架构:从 Anaconda 到 PyCharm 的四级防护体系
运维·ide·人工智能·windows·python·架构·pycharm
m0_751336391 小时前
机器学习赋能多尺度材料模拟:前沿技术会议邀您共探
人工智能·深度学习·机器学习·第一性原理·分子动力学·vasp·复合材料
暴躁茹2 小时前
C++中,std::async 一个用于异步编程的工具
开发语言·c++