图像滤波之高斯滤波介绍
1 高斯滤波简介
了解高斯滤波之前,我们首先熟悉一下高斯噪声。高斯噪声是指它的概率密度函数服从高斯分布(即正态分布)的一类噪声。如果一个噪声,它的幅度分布服从高斯分布,而它的功率谱密度又是均匀分布的,则称它为高斯白噪声。高斯白噪声的二阶矩不相关,一阶矩为常数,是指先后信号在时间上的相关性,高斯白噪声包括热噪声和散粒噪声。
高斯滤波器是一类根据高斯函数的形状来选择权值的线性平滑滤波器。高斯平滑滤波器对于抑制服从正态分布的噪声非常有效。一维零均值高斯函数为:
g(x)=exp( -x^2/(2 sigma^2)
其中,高斯分布参数Sigma决定了高斯函数的宽度。对于图像处理来说,常用二维零均值离散高斯函数作平滑滤波器,高斯函数的图形:
2 高斯滤波函数
对于图像来说,高斯滤波器是利用高斯核的一个2维的卷积算子,用于图像模糊化(去除细节和噪声)。
1) 高斯分布
一维高斯分布:
二维高斯分布:
2) 高斯核
理论上,高斯分布在所有定义域上都有非负值,这就需要一个无限大的卷积核。实际上,仅需要取均值周围3倍标准差内的值,以外部份直接去掉即可。 如下图为一个标准差为1.0的整数值高斯核。
3 高斯滤波性质
高斯函数具有五个重要的性质,这些性质使得它在早期图像处理中特别有用.这些性质表明,高斯平滑滤波器无论在空间域还是在频率域都是十分有效的低通滤波器,且在实际图像处理中得到了工程人员的有效使用.高斯函数具有五个十分重要的性质,它们是:
(1)二维高斯函数具有旋转对称性,即滤波器在各个方向上的平滑程度是相同的.一般来说,一幅图像的边缘方向是事先不知道的,因此,在滤波前是无法确定一个方向上比另一方向上需要更多的平滑.旋转对称性意味着高斯平滑滤波器在后续边缘检测中不会偏向任一方向.
(2)高斯函数是单值函数.这表明,高斯滤波器用像素邻域的加权均值来代替该点的像素值,而每一邻域像素点权值是随该点与中心点的距离单调增减的.这一性质是很重要的,因为边缘是一种图像局部特征,如果平滑运算对离算子中心很远的像素点仍然有很大作用,则平滑运算会使图像失真.
(3)高斯函数的傅立叶变换频谱是单瓣的.正如下面所示,这一性质是高斯函数付立叶变换等于高斯函数本身这一事实的直接推论.图像常被不希望的高频信号所污染(噪声和细纹理).而所希望的图像特征(如边缘),既含有低频分量,又含有高频分量.高斯函数付立叶变换的单瓣意味着平滑图像不会被不需要的高频信号所污染,同时保留了大部分所需信号.
(4)高斯滤波器宽度(决定着平滑程度)是由参数σ表征的,而且σ和平滑程度的关系是非常简单的.σ越大,高斯滤波器的频带就越宽,平滑程度就越好.通过调节平滑程度参数σ,可在图像特征过分模糊(过平滑)与平滑图像中由于噪声和细纹理所引起的过多的不希望突变量(欠平滑)之间取得折衷.
(5)由于高斯函数的可分离性,较大尺寸的高斯滤波器可以得以有效地实现.二维高斯函数卷积可以分两步来进行,首先将图像与一维高斯函数进行卷积,然后将卷积结果与方向垂直的相同一维高斯函数卷积.因此,二维高斯滤波的计算量随滤波模板宽度成线性增长而不是成平方增长.
4 高斯滤波应用
高斯滤波后图像被平滑的程度取决于标准差。它的输出是领域像素的加权平均,同时离中心越近的像素权重越高。因此,相对于均值滤波(mean filter)它的平滑效果更柔和,而且边缘保留的也更好。
高斯滤波被用作为平滑滤波器的本质原因是因为它是一个低通滤波器,见下图。而且,大部份基于卷积平滑滤波器都是低通滤波器。
图.高斯滤波器(标准差=3像素)的频率响应。The spatial frequency axis is marked
in cycles per pixel, and hence no value above 0.5 has a real meaning。
5 高斯滤波步骤
(1)移动相关核的中心元素,使它位于输入图像待处理像素的正上方
(2)将输入图像的像素值作为权重,乘以相关核
(3)将上面各步得到的结果相加做为输出
6 高斯滤波源码(C语言版)
1 // gaosilvbo.cpp : 定义控制台应用程序的入口点。 2 // 3 4 #include "stdafx.h" 5 #include <stdlib.h> 6 #include <math.h> 7 8 typedef unsigned long DWORD; 9 typedef long LONG; 10 typedef unsigned short WORD; 11 typedef unsigned char BYTE; 12 13 typedef struct tagRGBQUAD { 14 BYTE rgbBlue; 15 BYTE rgbGreen; 16 BYTE rgbRed; 17 BYTE rgbReserved; 18 } RGBQUAD; 19 20 #pragma pack (2) /*指定按字节对齐*/ 21 typedef struct tagBITMAPFILEHEADER { 22 WORD bfType; 23 DWORD bfSize; 24 WORD bfReserved1; 25 WORD bfReserved2; 26 DWORD bfOffBits; 27 } BITMAPFILEHEADER; 28 29 //恢复对齐状态 30 typedef struct tagBITMAPINFOHEADER{ 31 DWORD biSize; 32 LONG biWidth; 33 LONG biHeight; 34 WORD biPlanes; 35 WORD biBitCount; 36 DWORD biCompression; 37 DWORD biSizeImage; 38 LONG biXPelsPerMeter; 39 LONG biYPelsPerMeter; 40 DWORD biClrUsed; 41 DWORD biClrImportant; 42 } BITMAPINFOHEADER; 43 44 unsigned char *pTempBmpBuf; //读入图像数据的指针 45 46 unsigned char *pBmpBuf; //读入图像数据的指针 47 48 49 int bmpWidth; //图像的宽 50 int bmpHeight; //图像的高 51 RGBQUAD *pColorTable; //颜色表指针 52 int biBitCount; //图像类型,每像素位数 53 54 bool readBmp(char *bmpName) 55 { 56 //二进制读方式打开指定的图像文件 57 58 FILE *fp=fopen(bmpName,"rb"); 59 if(fp==0) return 0; 60 61 62 //跳过位图文件头结构BITMAPFILEHEADER 63 fseek(fp, sizeof(BITMAPFILEHEADER),0); 64 65 //定义位图信息头结构变量,读取位图信息头进内存,存放在变量head中 66 BITMAPINFOHEADER head; 67 fread(&head, sizeof(BITMAPINFOHEADER), 1,fp); 68 69 //获取图像宽、高、每像素所占位数等信息 70 bmpWidth = head.biWidth; 71 bmpHeight = head.biHeight; 72 biBitCount = head.biBitCount; 73 74 75 //定义变量,计算图像每行像素所占的字节数(必须是的倍数) 76 int lineByte=(bmpWidth * biBitCount/8+3)/4*4; 77 78 //灰度图像有颜色表,且颜色表表项为 79 if(biBitCount==8){ 80 //申请颜色表所需要的空间,读颜色表进内存 81 pColorTable=new RGBQUAD[256]; 82 fread(pColorTable,sizeof(RGBQUAD),256,fp); 83 } 84 85 86 //申请位图数据所需要的空间,读位图数据进内存 87 pTempBmpBuf=new unsigned char[lineByte * bmpHeight]; 88 89 pBmpBuf=new unsigned char[lineByte * bmpHeight]; 90 fread(pTempBmpBuf,1,lineByte * bmpHeight,fp); 91 fseek(fp, 1078,0); 92 fread(pBmpBuf,1,lineByte * bmpHeight,fp); 93 94 //关闭文件 95 fclose(fp); 96 return 1; 97 } 98 99 bool saveBmp(char *bmpName, unsigned char *imgBuf, int width, int height,int biBitCount, RGBQUAD *pColorTable) 100 { 101 102 if(!imgBuf) 103 return 0; 104 105 //颜色表大小,以字节为单位,灰度图像颜色表为字节,彩色图像颜色表大小为 106 int colorTablesize=0; 107 if(biBitCount==8) 108 colorTablesize=1024; 109 110 //待存储图像数据每行字节数为的倍数 111 int lineByte=(width * biBitCount/8+3)/4*4; 112 113 //以二进制写的方式打开文件 114 FILE *fp=fopen(bmpName,"wb"); 115 if(fp==0) return 0; 116 117 //申请位图文件头结构变量,填写文件头信息 118 BITMAPFILEHEADER fileHead; 119 fileHead.bfType = 0x4D42;//bmp类型 120 121 //bfSize是图像文件个组成部分之和 122 fileHead.bfSize= sizeof(BITMAPFILEHEADER) 123 + sizeof(BITMAPINFOHEADER) 124 + colorTablesize + lineByte*height; 125 126 fileHead.bfReserved1 = 0; 127 fileHead.bfReserved2 = 0; 128 129 //bfOffBits是图像文件前个部分所需空间之和 130 fileHead.bfOffBits=54+colorTablesize; 131 132 //写文件头进文件 133 fwrite(&fileHead, sizeof(BITMAPFILEHEADER),1, fp); 134 135 //申请位图信息头结构变量,填写信息头信息 136 BITMAPINFOHEADER head; 137 head.biBitCount=biBitCount; 138 head.biClrImportant=0; 139 head.biClrUsed=0; 140 head.biCompression=0; 141 head.biHeight=height; 142 head.biPlanes=1; 143 head.biSize=40; 144 head.biSizeImage=lineByte*height; 145 head.biWidth=width; 146 head.biXPelsPerMeter=0; 147 head.biYPelsPerMeter=0; 148 149 //写位图信息头进内存 150 fwrite(&head, sizeof(BITMAPINFOHEADER),1, fp); 151 152 //如果灰度图像,有颜色表,写入文件 153 if(biBitCount==8) 154 fwrite(pColorTable, sizeof(RGBQUAD),256, fp); 155 156 //写位图数据进文件 157 fwrite(imgBuf, height*lineByte, 1, fp); 158 159 //关闭文件 160 fclose(fp); 161 return 1; 162 } 163 164 int _tmain(int argc, _TCHAR* argv[]) 165 { 166 //读入指定BMP文件进内存 167 char readPath[]="guass_test.bmp"; 168 readBmp(readPath); 169 //输出图像的信息 170 printf("width=%d,height=%d,biBitCount=%d\n", 171 bmpWidth,bmpHeight,biBitCount); 172 173 //每行字节数 174 int lineByte=(bmpWidth*biBitCount/8+3)/4*4; 175 //定义最终写入的数据体 176 //pBmpBuf=new unsigned char[lineByte * bmpHeight]; 177 //循环变量,图像的坐标 178 int y,x; 179 180 //循环变量,针对彩色图像,遍历每像素的三个分量 181 int k; 182 //单精度变量暂存计算后的灰度值(针对灰度图像) 183 float TempNum; 184 //指向TempBmpbuf的指针 185 unsigned char *TemPtr; 186 //指向BmpBuf的指针 187 unsigned char *Ptr; 188 //定义*3的模板(拉普拉斯) 189 float CoefArray[9]={1.0f,2.0f,1.0f,2.0f,4.0f,2.0f,1.0f,2.0f,1.0f}; 190 //定义模板前乘的系数(拉普拉斯) 191 float coef=(float)(1.0/16.0);; 192 193 //lapulas滤波 194 if(biBitCount==8){//对于灰度图像 195 for(y=1;y<bmpHeight-1;y++){ 196 for(x=0;x<bmpWidth-1;x++){ 197 198 TemPtr=pTempBmpBuf+y*lineByte+x; 199 Ptr=pBmpBuf+y*lineByte+x; 200 201 TempNum=(float)((unsigned char)*(TemPtr+lineByte-1))*CoefArray[0]; 202 TempNum+=(float)((unsigned char)*(TemPtr+lineByte))*CoefArray[1]; 203 TempNum+=(float)((unsigned char)*(TemPtr+lineByte+1))*CoefArray[2]; 204 TempNum+=(float)((unsigned char)*(TemPtr-1))*CoefArray[3]; 205 TempNum+=(float)((unsigned char)*TemPtr)*CoefArray[4]; 206 TempNum+=(float)((unsigned char)*(TemPtr+1))*CoefArray[5]; 207 TempNum+=(float)((unsigned char)*(TemPtr-lineByte-1))*CoefArray[6]; 208 TempNum+=(float)((unsigned char)*(TemPtr-lineByte))*CoefArray[7]; 209 TempNum+=(float)((unsigned char)*(TemPtr-lineByte+1))*CoefArray[8]; 210 211 TempNum*=coef; 212 213 if(TempNum>255.0) *Ptr =(BYTE)255; 214 else if(TempNum<0.0) 215 *Ptr =(unsigned char)fabs(TempNum); 216 //用到了fabs函数,需要添加math.h头文件 217 else *Ptr=(char)TempNum; 218 } 219 } 220 } 221 222 else if(biBitCount==24){//彩色图像 223 for(y=0;y<bmpHeight/2;y++){ 224 for(x=0;x<bmpWidth/2;x++){ 225 for(k=0;k<3;k++)//每像素RGB三个分量分别置才变成黑色 226 *(pBmpBuf+y*lineByte+x*3+k)=0; 227 } 228 } 229 } 230 //将图像数据存盘 231 char writePath[]="gauss_result.BMP"; 232 saveBmp(writePath, pBmpBuf, bmpWidth, 233 bmpHeight, biBitCount, pColorTable); 234 //清除缓冲区,pBmpBuf和pColorTable是全局变量,在文件读入时申请的空间 235 delete []pBmpBuf; 236 delete []pTempBmpBuf; 237 if(biBitCount==8) 238 delete []pColorTable; 239 return 0; 240 }
高斯滤波处理之后: 高斯滤波处理之前:
图像滤波之高斯滤波介绍相关推荐
- 【图像处理】——图像滤波(Python+opencv实现三种方法:均值滤波、中值滤波、高斯滤波等)
目录 一.什么是滤波以及滤波的目的? 二.均值滤波(cv2.blur()) 1.原理 2.关键代码 3.封装代码 二.中值滤波(cv2.medianBlur()) 1.原理 2.关键代码 3.封装代码 ...
- 通过matlab编程,对该图像分别添加高斯噪声和椒盐噪声(参数自定),并使用均值滤波、高斯滤波和中值滤波进行去噪。
分别添加高斯和椒盐噪声 im = imread('C:\Users\Administrator\Desktop\123456.jpg');% 1)生成含有高斯噪声.椒盐噪声的图像 % imnoise ...
- Python 图像处理 | 图像平滑之均值滤波、方框滤波、高斯滤波及中值滤波
作者 | 杨秀璋,责编 | 夕颜 题图 | 视觉中国 出品 | CSDN博客 本篇文章主要讲解Python调用OpenCV实现图像平滑,包括四个算法:均值滤波.方框滤波.高斯滤波和中值滤波.全文均是 ...
- 【图像处理】【计算机视觉】线性邻域滤波专场:方框滤波、均值滤波与高斯滤波...
首先注意点:关于OpenCV中的函数,有老的数据结构,还有新的opencv2的数据结构,一般地区别就是IplImage*与Mat的区别,两者大致分别对应着C和C++内的两个功能一样,但是函数名称有别. ...
- 灰度图像--图像增强 平滑之均值滤波、高斯滤波
灰度图像--图像增强 平滑之均值滤波.高斯滤波 目录(?)[+] 开篇废话 均值滤波 数学 效果 代码 高斯滤波 数学 效果 代码 总结 学习DIP第30天 转载请标明本文出处: ...
- [Python图像处理] 四十一.Python图像平滑万字详解(均值滤波、方框滤波、高斯滤波、中值滤波、双边滤波)
该系列文章是讲解Python OpenCV图像处理知识,前期主要讲解图像入门.OpenCV基础用法,中期讲解图像处理的各种算法,包括图像锐化算子.图像增强技术.图像分割等,后期结合深度学习研究图像识别 ...
- [Python图像处理] 四.图像平滑之均值滤波、方框滤波、高斯滤波及中值滤波
该系列文章是讲解Python OpenCV图像处理知识,前期主要讲解图像入门.OpenCV基础用法,中期讲解图像处理的各种算法,包括图像锐化算子.图像增强技术.图像分割等,后期结合深度学习研究图像识别 ...
- [Python从零到壹] 五十五.图像增强及运算篇之图像平滑(均值滤波、方框滤波、高斯滤波)
又是一年1024,首先,祝大家节日快乐! 欢迎大家来到"Python从零到壹",在这里我将分享约200篇Python系列文章,带大家一起去学习和玩耍,看看Python这个有趣的世界 ...
- 《OpenCv视觉之眼》Python图像处理五 :Opencv图像去噪处理之均值滤波、方框滤波、中值滤波和高斯滤波
本专栏主要介绍如果通过OpenCv-Python进行图像处理,通过原理理解OpenCv-Python的函数处理原型,在具体情况中,针对不同的图像进行不同等级的.不同方法的处理,以达到对图像进行去噪.锐 ...
- 《OpenCV3编程入门》学习笔记6 图像处理(一)线性滤波:方框滤波、均值滤波、高斯滤波
第6章 图像处理 6.1 线性滤波:方框滤波.均值滤波.高斯滤波 6.1.1 图像滤波与滤波器 1.图像滤波:在尽量保留图像细节特征的条件下对目标图像的噪声进行抑制 目的: (1)抽出对象的特征作为图 ...
最新文章
- c# response输出文件实例(14)
- ML 自学者周刊:第 1 期
- Spring-Cloud中常见的服务组件
- Minimum Inversion Number HDU - 1394(权值线段树/树状数组)
- 【实践案例】Databricks 数据洞察 Delta Lake 在基智科技(STEPONE)的应用实践
- 官方 STM32F303ZE Nucleo-144开发板 按键使用
- Express框架学习笔记-express路由参数
- python傅里叶谐波分析_利用傅里叶谐波分析法的时序数据周期迭代辨识算法
- web前端面试题总结
- input 文件提交 按钮制作
- linux命令 复制文件,linux复制文件的命令是什么?
- C++ 读取和写入txt文件
- amd 服务器cpu型号怎么看,AMD CPU型号识别方法图解
- 百度、360、搜狗、神马的SEO搜索结果php爬取排名。
- 【什么是Cookie、Session】
- html文本怎么打印出来,如何把一个html文件直接打印出来(200分)
- react-router 与react-reduct 配合使用时,页面不刷新问题
- Chrome 66之后禁止网页声音自动播放问题解决
- Url参数是另一段带参Url
- ROS示例----导航功能包Husky_exploration
热门文章
- boost::mp11::mp_fold_q相关用法的测试程序
- boost::mp11::mp_fill相关用法的测试程序
- boost::hana::partition用法的测试程序
- boost::fusion::fused用法的测试程序
- boost::endian模块实现reverse的测试程序
- Boost:移动容器的测试程序
- VTK:可视化之KochSnowflake
- VTK:相互作用之InteractorStyleUser
- VTK:InfoVis之KMeansClustering
- OpenCV在图像中寻找轮廓的实例(附完整代码)