OpenCV(九)形态学操作4--礼帽与黑帽(顶帽与底帽)
opencv
OpenCV: 开源计算机视觉库
项目地址:https://gitcode.com/gh_mirrors/opencv31/opencv
免费下载资源
·
目录
一、顶帽运算(礼帽)
取出亮度高的地方
顶帽运算 = 原图像 - 开运算
开运算可以消除暗背景下的高亮区域,那么如果用原图减去开运算结果就可以得到原图中灰度较亮的区域,所以又称白顶帽变换。
C++:
//顶帽运算
void TopHat()
{
//开运算
Mat kernel = getStructuringElement(MORPH_RECT, Size(19, 19)); //创建结构元
// 矩形卷积核 尺寸为(19,19)宽高
morphologyEx(img, dst, MORPH_OPEN, kernel, Point(-1, -1)); // 形态学处理--开运算
// 原图 新图 开运算 卷积核 锚点
imshow("开运算", dst); // 显示形态学处理后的效果
//顶帽运算(白顶帽运算)
dst = img - dst;
//morphologyEx(img, dst, MORPH_TOPHAT, kernel, Point(-1, -1), 1); // 形态学处理--开帽变换
imshow("顶帽运算", dst);
}
python:
# 顶帽(原-开)
def TopHat():
tophat = cv2.morphologyEx(img, cv2.MORPH_TOPHAT, (7, 7), iterations=5)
# 类型 卷积核 迭代次数
cv2.imshow('TopHat', tophat)
二、底帽运算(黑帽)
取出亮度低的地方
底帽运算 = 原图像 - 闭运算
闭运算可以删除亮背景下的暗区域,那么用原图减去闭运算结果就可以得到原图像中灰度较暗的区域,所以又称黑底帽变换。
C++:
//底帽运算
void BlackHat()
{
//闭运算
Mat kernel = getStructuringElement(MORPH_RECT, Size(19, 19)); //创建结构元
// 矩形卷积核 尺寸为(19,19)宽高
morphologyEx(img, dst, MORPH_CLOSE, kernel, Point(-1, -1)); // 形态学处理--开运算
// 原图 新图 闭运算 卷积核 锚点
imshow("闭运算", dst); // 显示形态学处理后的效果
//底帽运算(黑帽运算)
//morphologyEx(img, dst, MORPH_BLACKHAT, kernel, Point(-1, -1), 1); // 形态学处理--底帽变换
dst = img - dst;
imshow("底帽运算", dst);
}
python:
# 底帽(原-闭)
def BlackHat():
blackhat = cv2.morphologyEx(img, cv2.MORPH_BLACKHAT, (7, 7), iterations=5)
# 类型 卷积核 迭代次数
cv2.imshow('BlackHat', blackhat)
只有这样可能看不出来用途,再举一个实用的例子:
三、底帽运算应用(二值图像底帽运算)
目的:得到清晰的二值图像。
底帽效果:取出亮度较暗的区域。
1、原图转灰度图,再转二值图像
//灰度图及二值化
cvtColor(img, grayImage, COLOR_BGR2GRAY);
imshow("灰度图(原图)", grayImage);
threshold(grayImage, binImage, 0, 255, THRESH_OTSU);
imshow("二值化图像", binImage);
可以看出,虽然圆环被分割为目标区域,但左侧背景区域有很大一部分也被分割为目标,并且该区域面积较大,难以通过开操作或闭操作去除。
为了取出亮度低的地方,接下来我们通过底帽操作来进行处理。首先对原图进行底帽处理,然后再对底帽处理的结果进行二值化,最后对处理结果进行一轮闭操作。
2、灰度图底帽处理
kernel = getStructuringElement(MORPH_RECT, Size(31, 31)); //修改结构元
morphologyEx(grayImage, dst, MORPH_BLACKHAT, kernel, Point(-1, -1), 1); // 形态学处理--底帽变换
imshow("底帽运算", dst);
threshold(dst, binImage, 0, 255, THRESH_OTSU);
imshow("底帽处理后的二值化图像", binImage);
3、二值图闭运算
//3、二值图闭运算处理
kernel = getStructuringElement(MORPH_RECT, Size(3, 3)); //修改结构元
morphologyEx(binImage, binImage, MORPH_CLOSE, kernel, Point(-1, -1)); // 形态学处理--闭运算
imshow("闭运算处理后的二值化图像", binImage);
代码
//二值图像底帽运算
void Bin_BlackHat()
{
Mat kernel = getStructuringElement(MORPH_RECT, Size(19, 19)); //创建结构元
//1、灰度图及二值化
cvtColor(img, grayImage, COLOR_BGR2GRAY);
imshow("灰度图(原图)", grayImage);
threshold(grayImage, binImage, 0, 255, THRESH_OTSU);
imshow("二值化图像", binImage);
//2、对灰度图底帽处理
kernel = getStructuringElement(MORPH_RECT, Size(31, 31)); //修改结构元
morphologyEx(grayImage, dst, MORPH_BLACKHAT, kernel, Point(-1, -1), 1); // 形态学处理--底帽变换
imshow("底帽运算", dst);
threshold(dst, binImage, 0, 255, THRESH_OTSU);
imshow("底帽处理后的二值化图像", binImage);
//3、二值图闭运算处理
kernel = getStructuringElement(MORPH_RECT, Size(3, 3)); //修改结构元
morphologyEx(binImage, binImage, MORPH_CLOSE, kernel, Point(-1, -1)); // 形态学处理--闭运算
imshow("闭运算处理后的二值化图像", binImage);
}
总代码
//开运算与闭运算(形态学)
#include <iostream>
#include <opencv2/opencv.hpp>
using namespace cv;
using namespace std;
Mat img, dst;
Mat binImage, grayImage;
//图像初始化
void Image_Init()
{
img = imread("Resource/test9.jpg");
dst = Mat::zeros(img.size(), img.type());
if (img.empty())
{
printf("图像加载失败");
exit(0);
}
}
//顶帽运算
void TopHat()
{
//开运算
Mat kernel = getStructuringElement(MORPH_RECT, Size(19, 19)); //创建结构元
// 矩形卷积核 尺寸为(19,19)宽高
morphologyEx(img, dst, MORPH_OPEN, kernel, Point(-1, -1)); // 形态学处理--开运算
// 原图 新图 开运算 卷积核 锚点
imshow("开运算", dst); // 显示形态学处理后的效果
//顶帽运算(白顶帽运算)
dst = img - dst;
//morphologyEx(img, dst, MORPH_TOPHAT, kernel, Point(-1, -1), 1); // 形态学处理--开帽变换
imshow("顶帽运算", dst);
}
//底帽运算
void BlackHat()
{
//闭运算
Mat kernel = getStructuringElement(MORPH_RECT, Size(19, 19)); //创建结构元
// 矩形卷积核 尺寸为(19,19)宽高
morphologyEx(img, dst, MORPH_CLOSE, kernel, Point(-1, -1)); // 形态学处理--闭运算
// 原图 新图 闭运算 卷积核 锚点
imshow("闭运算", dst); // 显示形态学处理后的效果
//底帽运算(黑帽运算)
//morphologyEx(img, dst, MORPH_BLACKHAT, kernel, Point(-1, -1), 1); // 形态学处理--底帽变换
dst = img - dst;
imshow("底帽运算", dst);
}
//二值图像底帽运算
void Bin_BlackHat()
{
Mat kernel = getStructuringElement(MORPH_RECT, Size(19, 19)); //创建结构元
//1、灰度图及二值化
cvtColor(img, grayImage, COLOR_BGR2GRAY);
imshow("灰度图(原图)", grayImage);
threshold(grayImage, binImage, 0, 255, THRESH_OTSU);
imshow("二值化图像", binImage);
//2、对灰度图底帽处理
kernel = getStructuringElement(MORPH_RECT, Size(31, 31)); //修改结构元
morphologyEx(grayImage, dst, MORPH_BLACKHAT, kernel, Point(-1, -1), 1); // 形态学处理--底帽变换
imshow("底帽运算", dst);
threshold(dst, binImage, 0, 255, THRESH_OTSU);
imshow("底帽处理后的二值化图像", binImage);
//3、二值图闭运算处理
kernel = getStructuringElement(MORPH_RECT, Size(3, 3)); //修改结构元
morphologyEx(binImage, binImage, MORPH_CLOSE, kernel, Point(-1, -1)); // 形态学处理--闭运算
imshow("闭运算处理后的二值化图像", binImage);
}
//显示图像
void Show()
{
imshow("原图", img);
}
int main()
{
Image_Init(); //图像初始化
//TopHat(); //顶帽运算
//BlackHat(); //底帽运算
Bin_BlackHat(); //二值图像底帽运算
Show(); //显示原图像
waitKey(0);
return 0;
}
# 形态学(膨胀、腐蚀、开闭运算、顶帽与底帽)
import cv2
# 膨胀
def Dilate():
# 膨胀
dilate = cv2.dilate(img, kernel=(7, 7), iterations=1)
# 卷积核大小 迭代次数
cv2.imshow("dilate", dilate)
# 腐蚀
def Enrode():
# 腐蚀
erode = cv2.erode(img, kernel=(7, 7), iterations=5)
# 卷积核大小 迭代次数
cv2.imshow("erode", erode)
# 开运算(先腐后膨)
def Open():
open = cv2.morphologyEx(img, cv2.MORPH_OPEN, (7, 7), iterations=5)
# 类型 卷积核大小 迭代次数
cv2.imshow('open', open)
# 闭运算(先膨后腐)
def Close():
close = cv2.morphologyEx(img, cv2.MORPH_CLOSE, (7, 7), iterations=5)
# 类型 卷积核大小 迭代次数
cv2.imshow('close', close)
# 顶帽(原-开)
def TopHat():
tophat = cv2.morphologyEx(img, cv2.MORPH_TOPHAT, (7, 7), iterations=5)
# 类型 卷积核 迭代次数
cv2.imshow('TopHat', tophat)
# 底帽(原-闭)
def BlackHat():
blackhat = cv2.morphologyEx(img, cv2.MORPH_BLACKHAT, (7, 7), iterations=5)
# 类型 卷积核 迭代次数
cv2.imshow('BlackHat', blackhat)
if __name__ == '__main__':
# 读取图片
img = cv2.imread("Resource/test5.jpg")
cv2.imshow("img", img)
Dilate() #膨胀
Enrode() #腐蚀
Open() #开运算
Close() #闭运算
TopHat() #顶帽运算
BlackHat() #底帽运算
cv2.waitKey(0)
参考资料
https://blog.csdn.net/weixin_41695564/article/details/79935028
GitHub 加速计划 / opencv31 / opencv
162
15
下载
OpenCV: 开源计算机视觉库
最近提交(Master分支:4 个月前 )
796adf5d
Avoid adding value to nullptr 16 小时前
1a6ef7e0
Fixed Android build with Vulkan support. 19 小时前
更多推荐
已为社区贡献19条内容
所有评论(0)