首页 > 其他分享 >OpenCV_自定义线性滤波(filter2D)应用详解

OpenCV_自定义线性滤波(filter2D)应用详解

时间:2024-09-25 09:21:28浏览次数:14  
标签:Mat 自定义 卷积 滤波 像素 OpenCV 图像 filter2D

OpenCV filter2D将图像与内核进行卷积,将任意线性滤波器应用于图像。支持就地操作。当孔径部分位于图像之外时,该函数根据指定的边界模式插值异常像素值。

卷积核本质上是一个固定大小的系数数组,数组中的某个元素被作为锚点(一般是数组的中心)。

上面讲了线性滤波的实质就是计算相关,相关计算的具体步骤如下:

  • 将卷积核的锚点放在某个目标像素上,卷积核的其他部分就会覆盖目标像素的邻近像素;
  • 将卷积核上的系数与被覆盖的像素的值相乘,然后将积加总;
  • 将加总的和赋予目标像素
  • 对图像上的所有像素都应用以上步骤,直到每个像素都被当作目标像素进行了计算。

函数:

void cv::filter2D(InputArray	src,
				OutputArray		dst,
				int				ddepth,
				InputArray		kernel,
				Point			anchor = Point(-1, -1),
				double			delta = 0,
				int				borderType = BORDER_DEFAULT
)

src 输入图像

       dst  输出图像,与 src 大小相同、通道数相同

       ddepth  目标图像的所需深度

        kernel 卷积核(或者更确切地说是相关核),单通道浮点矩阵;如果要将不同的内核应用于                        不同的通道,请使用 split 将图像分割为单独的颜色平面并单独处理它们。

        anchor 内核的锚点,指示内核中过滤点的相对位置;锚应该位于内核内;默认值(-1,-1)                      表示锚点位于内核中心。

        delta  在将过滤像素存储到 dst 之前添加到过滤像素的可选值。

        borderType 像素外推方法。可以选以下几种:BORDER_CONSTANT,BORDER_REPLICATE,BORDER_REFLECT,BORDER_REFLECT_101,BORDER_TRANSPARENT,BORDER_REFLECT101,BORDER_DEFAULT,BORDER_ISOLATED。

OpenCV filter2D函数应用

使用OpenCV filter2D函数,通过改变卷积核(kernel)可达成不同的滤波效果。下面就OpenCV filter2D函数的几种常用场景做说明,并以实例做演示。

图像锐化

图像锐化使用的卷积核如下:

        Mat kernel = (Mat_<char>(3, 3) << 0, -1, 0, -1, 5, -1, 0, -1, 0);

下面以实例演示图像锐化操作及锐化效果,示例代码如下:

void QuickDemo::nineth(Mat image) {
    Mat sharpenImage;
	Mat kernel = (Mat_<int>(3, 3) << 0, -1, 0, -1, 5, -1, 0, -1, 0);
	filter2D(image, sharpenImage, image.depth(), kernel, Point(-1, -1), 0);
	namedWindow("锐化", WINDOW_AUTOSIZE);
	imshow("锐化", sharpenImage);
}

可以看到经过Filter2D滤波后的图像变得更清晰。

均值滤波

OpenCV filter2D函数实现均值滤波的卷积核如下:

Mat kernel = (Mat_<float>(3, 3) << 1, 1, 1, 1, 1, 1, 1, 1, 1) / 9;

下面以实例演示filter2D实现图像均值滤波操作及滤波效果,示例代码如下:

void QuickDemo::nineth(Mat image) {
	Mat blurImage;
	Mat kernel = (Mat_<float>(3, 3) << 1, 1, 1, 1, 1, 1, 1, 1, 1)/9;
	filter2D(image, blurImage, image.depth(), kernel, Point(-1, -1));
	namedWindow("均值滤波", WINDOW_AUTOSIZE);
	imshow("均值滤波", blurImage);
}

可以看出,均值滤波可以去除图像椒盐噪声,达到磨皮效果。

高斯滤波

OpenCV filter2D函数实现高斯滤波的卷积核可由高斯核转换得到,方法如下:

Mat kernelGaussian = getGaussianKernel(9, 1.5);
Mat  kernel = kernelGaussian * kernelGaussian.t();

 getGaussianKernel( int ksize, double sigma, int ktype = CV_32F );

参数说明:

  • ksize:高斯核的大小。它必须是大于零的奇数。

  • sigma:高斯核的标准差。如果它等于零,那么根据ksize自动选择。

  • ktype:矩阵的类型。默认值为CV_32F

返回值:

一个ksize x 1的列矩阵,表示高斯核。

下面以实例演示filter2D实现图像高斯滤波操作及滤波效果,示例代码如下:

void QuickDemo::nineth(Mat image) {
	Mat gauBlurImage;
	//Mat kernel = (Mat_<float>(3, 3) << 1, 1, 1, 1, 1, 1, 1, 1, 1)/9;
	Mat kernelGaussian = getGaussianKernel(9, 1.5);
	Mat  kernel = kernelGaussian * kernelGaussian.t();
	filter2D(image, gauBlurImage, image.depth(), kernel, Point(-1, -1));
	namedWindow("高斯滤波", WINDOW_AUTOSIZE);
	imshow("高斯滤波", gauBlurImage);
}

可以看出,同样filter2D均高斯滤波同样可以去除图像椒盐噪声,达成磨皮效果,且所需次数更少。

边缘检测

 filter2D还可以使用sobel内核实现边缘检测,soble内核如下:

Mat sobelX = (Mat_<float>(3, 3) << -1, 0, 1,-2, 0, 2,-1, 0, 1);
Mat sobelY = (Mat_<float>(3, 3) << -1, -2, -1,0, 0, 0,1, 2, 1);

下面以实例演示filter2D 用sobel核实现图像边缘检测操作及滤波效果,示例代码如下:

void QuickDemo::nineth(Mat image) {
	threshold(image, image, 200, 255, THRESH_BINARY);

	Mat sobelX = (Mat_<float>(3, 3) << -1, 0, 1, -2, 0, 2, -1, 0, 1);
	Mat sobelY = (Mat_<float>(3, 3) << -1, -2, -1, 0, 0, 0, 1, 2, 1);

	Mat edges, edgesX, edgesY;
	filter2D(image, edgesX, CV_16S, sobelX);
	filter2D(image, edgesY, CV_16S, sobelY);

	convertScaleAbs(edgesX, edgesX);
	convertScaleAbs(edgesY, edgesY);
	addWeighted(edgesX,0.5,edgesY,0.5,0,edges);
	namedWindow("边缘检测", WINDOW_AUTOSIZE);
	imshow("边缘检测", edges);
}

 可以看出确实检测到了边缘,效果并不是很好。

        filter2D还可以使用Prewitt核,实现边缘检测。Prewitt核如下:

        Mat prewitt_x = (Mat_<int>(3, 3) << -1, 0, 1, -1, 0, 1, -1, 0, 1);
        Mat prewitt_y = (Mat_<int>(3, 3) << -1, -1, -1,0, 0, 0, 1, 1, 1);

        下面以实例演示filter2D 用Prewitt核实现图像边缘检测操作及滤波效果,示例代码如下:

void QuickDemo::nineth(Mat image) {
	threshold(image, image, 127, 255, THRESH_BINARY);

	Mat prewitt_x = (Mat_<int>(3, 3) << -1, 0, 1, -1, 0, 1, -1, 0, 1);
	Mat prewitt_y = (Mat_<int>(3, 3) << -1, -1, -1, 0, 0, 0, 1, 1, 1);

	Mat edges, edgesX, edgesY;
	filter2D(image, edgesX, CV_16S, prewitt_x );
	filter2D(image, edgesY, CV_16S, prewitt_y );

	convertScaleAbs(edgesX, edgesX);
	convertScaleAbs(edgesY, edgesY);
	addWeighted(edgesX,0.5,edgesY,0.5,0,edges);
	namedWindow("边缘检测", WINDOW_AUTOSIZE);
	imshow("边缘检测", edges);
}

从结果可以看出,filter2D使用Prewitt核检测边缘的结果,与使用sobel核边缘检测的结果是有差异的。

标签:Mat,自定义,卷积,滤波,像素,OpenCV,图像,filter2D
From: https://blog.csdn.net/qq_34800671/article/details/142481681

相关文章

  • vue自定义指令实现打字效果
    实现如通义灵码官网关于代码片段中,当鼠标hover上代码上时,出现打字效果,示例地址:https://tongyi.aliyun.com/lingma?spm=5176.28508143.J_ahRFo5CaAe_asSOaCgS4J.14.5421154auHz4xJ&scm=20140722.M_185502201.P_131.MO_2276-ID_10360025-MID_10360025-CID_31292-ST_10352-V_1通过vu......
  • 多校园信息付费发布顶置自定义表单小程序开源版开发
    多校园信息付费发布顶置自定义表单小程序开源版开发为校园管理和互动提供了强大的支持,包括用户端和运营后台两大部分。用户端允许学生和教职工方便地访问各种功能模块,而运营后台则使管理员能够高效地管理和配置系统。产品支持自定义模块和表单,允许根据需求创建各种功能,例如表白墙、......
  • 我无法在我的项目 Pycharm 中导入 opencv-python
    (myvenv)PSE:\Python>pipinstallopencv-pythonCollectingopencv-pythonUsingcachedopencv-python-4.10.0.84.tar.gz(95.1MB)Installingbuilddependencies...errorerror:subprocess-exited-with-error×pipsubprocesstoinstallbuilddepe......
  • go基础-10.自定义数据类型
    在Go语言中,自定义类型指的是使用type关键字定义的新类型,它可以是基本类型的别名,也可以是结构体、函数等组合而成的新类型。自定义类型可以帮助我们更好地抽象和封装数据,让代码更加易读、易懂、易维护自定义类型结构体就是自定义类型中的一种除此之外我们使用自定义类型,还可......
  • 子比主题美化-右上角显示用户自定义头像
    前言使用子比主题的都会发现,在右上方不管用户有没有自定义过头像,都只会显示默认的头像,这就很不科学,也不够个性,所以就有了这个教程,让右上角显示用户自定义的头像效果对比修改前修改后教程开始宝塔面板路径:wp-content/themes/zibll/inc/functions/zib-header.php 156行-......
  • ARS展览项目(二)——环境搭建:opencv、dlib、VS2017
    先说用到的软件和函数库VS2017——我用VS2017社区版来开发,原因是软件免费而且好用,本项目用C++来做opencv——OpenComputerVision是计算机视觉的库,有多种语言的接口,而且函数库也很丰富dlib——Dlib是一个包含机器学习算法的C++开源工具包,提供大量的机器学习/图像处理算法(网......