目录
实验原理
在OpenCV中,高斯滤波(Gaussian Filtering)是一种非常常用的图像平滑处理方法。它通过使用一个高斯核(即高斯分布函数)对图像进行卷积操作来去除噪声,同时保留尽可能多的边缘细节。高斯滤波器具有良好的频率响应特性,并且由于其平滑效果自然,因此在许多计算机视觉和图像处理任务中都有广泛应用。
函数原型
C++: void GaussianBlur(InputArray src, OutputArray dst,
Size ksize, double sigmaX, double sigmaY=0,
int borderType=BORDER_DEFAULT );
参数说明
src:输入图像,它可以是单通道或多通道图像。
dst:输出图像,与输入图像有相同的大小和类型。
ksize:高斯核的大小,通常是一个奇数大小的正方形,例如3x3, 5x5等。
sigmaX:在X方向上的高斯核的标准差;如果设置为0,则根据核大小计算标准差。
sigmaY:在Y方向上的高斯核的标准差;如果设置为0,则假设sigmaY=sigmaX。
borderType:边界处理类型,默认值为BORDER_DEFAULT,表示采用默认的边界扩展方式。
可以选择不同的边界处理方式,如BORDER_CONSTANT、BORDER_REFLECT等。
边界处理borderType参数决定了如何处理图像边缘的像素。
常见的边界处理方式包括:
•BORDER_CONSTANT:用指定的常数值填充边界。
•BORDER_REPLICATE:边界像素值向外扩展。
•BORDER_REFLECT:反射边界,如12345反射为45454。
•BORDER_WRAP:循环边界,如12345循环为34512。
高斯核的理解
高斯核是一个二维高斯函数的离散化版本,其权重随着距离中心点的距离增加而减少。当sigmaX或sigmaY设为0时,OpenCV会根据ksize自动计算标准差,使得高斯核具有一定的平滑效果。
示例代码1
下面是一个使用cv::GaussianBlur函数进行高斯滤波的示例代码:
#include "pch.h"
#include <opencv2/opencv.hpp>
#include <iostream>
int main(int argc, char** argv)
{
// 读取图像
cv::Mat src = cv::imread("02.png", cv::IMREAD_COLOR);
if (src.empty())
{
std::cout << "Error opening image" << std::endl;
return -1;
}
// 创建输出图像
cv::Mat dst;
// 定义卷积核大小
cv::Size kernelSize(9, 9); // 9x9的核
// 设置高斯核的标准差
double sigma = 2.0;
// 应用高斯滤波
cv::GaussianBlur(src, dst, kernelSize, sigma, sigma);
// 显示结果
cv::namedWindow("Original Image", cv::WINDOW_NORMAL);
cv::imshow("Original Image", src);
cv::namedWindow("Gaussian Blurred Image", cv::WINDOW_NORMAL);
cv::imshow("Gaussian Blurred Image", dst);
cv::waitKey(0);
return 0;
}
代码解释
1. 读取图像:使用cv::imread读取输入图像,并确保它是彩色图像。
2. 创建输出图像:创建一个新的cv::Mat对象来存储模糊后的结果。
3. 定义卷积核大小:定义一个9x9的卷积核大小。
4. 设置高斯核的标准差:设置高斯核的标准差sigma,用于控制高斯函数的宽度。
5. 应用高斯滤波:使用cv::GaussianBlur函数对图像进行高斯滤波。
6. 显示结果:使用cv::imshow函数显示原始图像和高斯模糊后的图像,并等待用户按键退出。
运行结果1
核大小的选择
卷积核的大小(ksize)决定了滤波器的效果。较大的核可以产生更强烈的平滑效果,但可能会丢失更多的细节;较小的核则可以保留更多细节,但平滑效果较弱。
标准差的选择
标准差(sigma)决定了高斯核的形状。较小的sigma值会使高斯核更加集中,较大的sigma值会使高斯核更加平坦。如果sigma设置为0,OpenCV会根据核大小自动计算一个合理的标准差值。
总结
高斯滤波是一种有效的图像平滑技术,通过使用高斯函数作为卷积核来减少噪声并保持图像的重要特征。通过调整卷积核的大小和标准差,可以控制平滑的程度。cv::GaussianBlur函数提供了方便的接口来实现高斯滤波,并且允许用户指定边界处理方式。
示例代码2
#include "pch.h"
#include <opencv2/opencv.hpp>
#include <iostream>
int main(int argc, char** argv)
{
// 加载图像
// 读取图像
cv::Mat src = cv::imread("03.png", cv::IMREAD_COLOR);
if (!src.data)
{
std::cout << "Error: Could not open or find the image" << std::endl;
return -1;
}
// 定义高斯核大小
cv::Size ksize(5, 5); // 通常使用奇数作为核大小
// 定义标准差
double sigma = 0; // 如果设置为0,则根据核大小自动计算标准差
// 创建一个用于存储结果的矩阵
cv::Mat dst;
// 应用高斯模糊
cv::GaussianBlur(src, dst, ksize, sigma);
// 显示原图和模糊后的图像
cv::namedWindow("Original Image", cv::WINDOW_NORMAL);
cv::imshow("Original Image", src);
cv::namedWindow("Blurred Image", cv::WINDOW_NORMAL);
cv::imshow("Blurred Image", dst);
// 等待用户按键后退出
cv::waitKey(0);
// 清理所有打开的窗口
cv::destroyAllWindows();
return 0;
}
运行结果2
实验代码3
// test.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//
#include "pch.h"
#include <opencv2/opencv.hpp>
#include <iostream>
using namespace cv;
using namespace std;
//#pragma comment(lib, "opencv_world450d.lib") //引用引入库
int main(int argc, char** argv)
{
Mat src, dst;
src = imread("2.jpeg");
if (!src.data)
{
printf("could not load image3...\n");
return -1;
}
//定义窗口名称
char input_title[] = "源图";
char output_title[] = "均值滤波";
//新建窗口
namedWindow(input_title, WINDOW_NORMAL);//原图波窗口
imshow(input_title, src);//原图显示
//均值滤波操作
blur(src, dst, Size(15, 15), Point(-1, -1));//均值滤波,Size里面都要奇数,正数。内核内数值分别表示宽,高。Point(-1,-1)表示锚点,一般取-1,表示锚点在核中心。
namedWindow(output_title, WINDOW_NORMAL);//均值滤波窗口
imshow(output_title, dst);
Mat gblur;
//高斯滤波操作
GaussianBlur(src, gblur, Size(15, 15), 11, 11);//高斯滤波
namedWindow("高斯滤波", WINDOW_NORMAL);
imshow("高斯滤波", gblur);
waitKey(0);
return 0;
}