基于 opencv图像去噪
-------------------开通头条号--------------------
|
实验名称 |
图像去噪 |
|
实验目的 |
1、掌握算术均值滤波器、几何均值滤波器、谐波和逆谐波均值滤波器进行图像去噪的算法 2、掌握利用中值滤波器进行图像去噪的算法 3、掌握自适应中值滤波算法 4、掌握自适应局部降低噪声滤波器去噪算法 5、掌握彩色图像去噪步骤 |
|
实验内容 |
1、均值滤波 具体内容:利用 OpenCV 对灰度图像像素进行操作,分别利用算术均值滤波器、几何均值滤波器、谐波和逆谐波均值滤波器进行图像去噪。模板大小为5*5。(注:请分别为图像添加高斯噪声、胡椒噪声、盐噪声和椒盐噪声,并观察滤波效果) 2、中值滤波 具体内容:利用 OpenCV 对灰度图像像素进行操作,分别利用 5*5 和 9*9尺寸的模板对图像进行中值滤波。(注:请分别为图像添加胡椒噪声、盐噪声和椒盐噪声,并观察滤波效果) 3、自适应均值滤波。 具体内容:利用 OpenCV 对灰度图像像素进行操作,设计自适应局部降低噪声滤波器去噪算法。模板大小 7*7(对比该算法的效果和均值滤波器的效果) 4、自适应中值滤波 具体内容:利用 OpenCV 对灰度图像像素进行操作,设计自适应中值滤波算法对椒盐图像进行去噪。模板大小 7*7(对比中值滤波器的效果) 5、彩色图像均值滤波 具体内容:利用 OpenCV 对彩色图像 RGB 三个通道的像素进行操作,利用算术均值滤波器和几何均值滤波器进行彩色图像去噪。模板大小为 5*5。 |
|
实验完成情况 |
1、 实验步骤:先为灰度图像添加高斯噪声、胡椒噪声、盐噪声和椒盐噪声,再分别利用算术均值滤波器、几何均值滤波器、谐波和逆谐波均值滤波器进行图像去噪。模板大小为5*5。 核心代码如下: 添加各类噪声: IplImage* AddGuassianNoise(IplImage* src) //添加高斯噪声 { IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); IplImage* noise = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); CvRNG rng = cvRNG(-1); cvRandArr(&rng,noise,CV_RAND_NORMAL,cvScalarAll(0),cvScalarAll(15)); cvAdd(src,noise,dst); return dst; } IplImage* AddPepperNoise(IplImage* src) //添加胡椒噪声,随机黑色点 { IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); cvCopy(src, dst); for(int k=0; k<8000; k++) { int i = rand()%src->height; int j = rand()%src->width; CvScalar s = cvGet2D(src, i, j); if(src->nChannels == 1) { s.val[0] = 0; } else if(src->nChannels==3) { s.val[0]=0; s.val[1]=0; s.val[2]=0; } cvSet2D(dst, i, j, s); } return dst; } IplImage* AddSaltNoise(IplImage* src) //添加盐噪声,随机白色点 { IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); cvCopy(src, dst); for(int k=0; k<8000; k++) { int i = rand()%src->height; int j = rand()%src->width; CvScalar s = cvGet2D(src, i, j); if(src->nChannels == 1) { s.val[0] = 255; } else if(src->nChannels==3) { s.val[0]=255; s.val[1]=255; s.val[2]=255; } cvSet2D(dst, i, j, s); } return dst; } IplImage* AddPepperSaltNoise(IplImage* src) //添加椒盐噪声,随机黑白点 { IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); cvCopy(src, dst); for(int k=0; k<8000; k++) { int i = rand()%src->height; int j = rand()%src->width; int m = rand()%2; CvScalar s = cvGet2D(src, i, j); if(src->nChannels == 1) { if(m==0) { s.val[0] = 255; } else { s.val[0] = 0; } } else if(src->nChannels==3) { if(m==0) { s.val[0]=255; s.val[1]=255; s.val[2]=255; } else { s.val[0]=0; s.val[1]=0; s.val[2]=0; } } cvSet2D(dst, i, j, s); } return dst; } 各类滤波器实现: //算术均值滤波器——模板大小5*5 IplImage* ArithmeticMeanFilter(IplImage* src) { IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); cvSmooth(src,dst,CV_BLUR,5); return dst; } //几何均值滤波器——模板大小5*5 IplImage* GeometryMeanFilter(IplImage* src) { IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); int row, col; int h=src->height; int w=src->width; double mul[3]; double dc[3]; int mn; //计算每个像素的去噪后color值 for(int i=0;i<src->height;i++){ for(int j=0;j<src->width;j++){ mul[0]=1.0; mn=0; //统计邻域内的几何平均值,邻域大小5*5 for(int m=-2;m<=2;m++){ row = i+m; for(int n=-2;n<=2;n++){ col = j+n; if(row>=0&&row<h && col>=0 && col<w){ CvScalar s = cvGet2D(src, row, col); mul[0] = mul[0]*(s.val[0]==0?1:s.val[0]); //邻域内的非零像素点相乘 mn++; } } } //计算1/mn次方 CvScalar d; dc[0] = pow(mul[0], 1.0/mn); d.val[0]=dc[0]; //统计成功赋给去噪后图像。 cvSet2D(dst, i, j, d); } } return dst; } //谐波均值滤波器——模板大小5*5 IplImage* HarmonicMeanFilter(IplImage* src) { IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); int row, col; int h=src->height; int w=src->width; double sum[3]; double dc[3]; int mn; //计算每个像素的去噪后color值 for(int i=0;i<src->height;i++){ for(int j=0;j<src->width;j++){ sum[0]=0.0; mn=0; //统计邻域,5*5模板 for(int m=-2;m<=2;m++){ row = i+m; for(int n=-2;n<=2;n++){ col = j+n; if(row>=0&&row<h && col>=0 && col<w){ CvScalar s = cvGet2D(src, row, col); sum[0] = sum[0]+(s.val[0]==0?255:255/s.val[0]); mn++; } } } CvScalar d; dc[0] = mn*255/sum[0]; d.val[0]=dc[0]; //统计成功赋给去噪后图像。 cvSet2D(dst, i, j, d); } } return dst; } //逆谐波均值大小滤波器——模板大小5*5 IplImage* InverseHarmonicMeanFilter(IplImage* src) { IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); //cvSmooth(src,dst,CV_BLUR,5); int row, col; int h=src->height; int w=src->width; double sum[3]; double sum1[3]; double dc[3]; double Q=2; //计算每个像素的去噪后color值 for(int i=0;i<src->height;i++){ for(int j=0;j<src->width;j++){ sum[0]=0.0; sum1[0]=0.0; //统计邻域 for(int m=-2;m<=2;m++){ row = i+m; for(int n=-2;n<=2;n++){ col = j+n; if(row>=0&&row<h && col>=0 && col<w){ CvScalar s = cvGet2D(src, row, col); sum[0] = sum[0]+pow(s.val[0]/255, Q+1); sum1[0] = sum1[0]+pow(s.val[0]/255, Q); } } } //计算1/mn次方 CvScalar d; dc[0] = (sum1[0]==0?0:(sum[0]/sum1[0]))*255; d.val[0]=dc[0]; //统计成功赋给去噪后图像。 cvSet2D(dst, i, j, d); } } return dst; } 实验结果如图所示:(从左至右,从上至下分别为原图像、加噪图像、算术均值处理图像、几何均值处理图像、谐波均值处理图像、逆谐波均值处理图像) (1)高斯噪声: (2)胡椒噪声: (3)盐噪声 (4)椒盐噪声 2、 实验步骤:先为灰度图像添加胡椒噪声、盐噪声和椒盐噪声,再分别利用5*5 和 9*9尺寸的模板对图像进行中值滤波。 核心代码如下: IplImage* MedianFilter_5_5(IplImage* src){ IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); cvSmooth(src,dst,CV_MEDIAN,5); return dst; } IplImage* MedianFilter_9_9(IplImage* src){ IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); cvSmooth(src,dst,CV_MEDIAN,9); return dst; } 实验结果如下图(灰度图像和加噪图像第一问中已给出,下面只列出分别利用5*5 和 9*9尺寸的模板对图像进行中值滤波后的图像): 灰度图像加胡椒噪声,分别利用5*5 和 9*9尺寸的模板对图像进行中值滤波。 灰度图像加盐噪声,分别利用5*5 和 9*9尺寸的模板对图像进行中值滤波。 灰度图像加椒盐噪声,分别利用5*5 和 9*9尺寸的模板对图像进行中值滤波。 3、 实验步骤:自适应均值滤波(以高斯噪声为例),先为灰度图像添加高斯噪声,再利用7*7尺寸的模板对图像进行自适应均值滤波。 核心代码如下: IplImage* SelfAdaptMeanFilter(IplImage* src){ IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); cvSmooth(src,dst,CV_BLUR,7); int row, col; int h=src->height; int w=src->width; int mn; double Zxy; double Zmed; double Sxy; double Sl; double Sn=100; for(int i=0;i<src->height;i++){ for(int j=0;j<src->width;j++){ CvScalar xy = cvGet2D(src, i, j); Zxy = xy.val[0]; CvScalar dxy = cvGet2D(dst, i, j); Zmed = dxy.val[0]; Sl=0; mn=0; for(int m=-3;m<=3;m++){ row = i+m; for(int n=-3;n<=3;n++){ col = j+n; if(row>=0&&row<h && col>=0 && col<w){ CvScalar s = cvGet2D(src, row, col); Sxy = s.val[0]; Sl = Sl+pow(Sxy-Zmed, 2); mn++; } } } Sl=Sl/mn; CvScalar d; d.val[0]=Zxy-Sn/Sl*(Zxy-Zmed); cvSet2D(dst, i, j, d); } } return dst; } 实验结果如图: 4、 实验步骤:自适应中值滤波(以椒盐噪声为例),先为灰度图像添加椒盐噪声,再利用7*7尺寸的模板对图像进行自适应中值滤波。 核心代码如下: IplImage* SelfAdaptMedianFilter(IplImage* src){ IplImage* dst = cvCreateImage(cvGetSize(src),src->depth,src->nChannels); int row, col; int h=src->height; int w=src->width; double Zmin,Zmax,Zmed,Zxy,Smax=7; int wsize; //计算每个像素的去噪后color值 for(int i=0;i<src->height;i++){ for(int j=0;j<src->width;j++){ //统计邻域 wsize=1; while(wsize<=3){ Zmin=255.0; Zmax=0.0; Zmed=0.0; CvScalar xy = cvGet2D(src, i, j); Zxy=xy.val[0]; int mn=0; for(int m=-wsize;m<=wsize;m++){ row = i+m; for(int n=-wsize;n<=wsize;n++){ col = j+n; if(row>=0&&row<h && col>=0 && col<w){ CvScalar s = cvGet2D(src, row, col); if(s.val[0]>Zmax){ Zmax=s.val[0]; } if(s.val[0]<Zmin){ Zmin=s.val[0]; } Zmed=Zmed+s.val[0]; mn++; } } } Zmed = Zmed/mn; CvScalar d; if((Zmed-Zmin)>0 && (Zmed-Zmax)<0){ if((Zxy-Zmin)>0 && (Zxy-Zmax)<0){ d.val[0]=Zxy; }else{ d.val[0]=Zmed; } cvSet2D(dst, i, j, d); break; } else { wsize++; if(wsize>3){ CvScalar d; d.val[0]=Zmed; cvSet2D(dst, i, j, d); break; } } } } } return dst; } 实验结果如图: 5、 实验步骤:利用 OpenCV 对彩色图像 RGB 三个通道的像素进行操作,利用算术均值滤波器和几何均值滤波器进行彩色图像去噪。模板大小为 5*5。 实验代码参照问题一,选择彩色图片、算术均值滤波器和几何均值滤波器进行彩色图像去噪。 实验结果如下图(以椒盐噪声为例): 利用算术均值滤波器: 利用几何均值滤波器: |
|
实验中的问题 |
实验问题:几何均值滤波以及谐波、逆谐波滤波没有对应的库函数 解决方法:通过学习书本对应章节,根据公式写出程序 |
|
实验结果 |
基于 opencv图像去噪的更多相关文章
- 基于OpenCV的火焰检测(一)——图像预处理
博主最近在做一个基于OpenCV的火焰检测的项目,不仅可以检测图片中的火焰,还可以检测视频中的火焰,最后在视频检测的基础上推广到摄像头实时检测.在做这个项目的时候,博主参考了很多相关的文献,用了很多种 ...
- 基于 opencv 的图像处理入门教程
前言 虽然计算机视觉领域目前基本是以深度学习算法为主,但实际上很多时候对图片的很多处理方法,并不需要采用深度学习的网络模型,采用目前成熟的图像处理库即可实现,比如 OpenCV 和 PIL ,对图片进 ...
- [转载]卡尔曼滤波器及其基于opencv的实现
卡尔曼滤波器及其基于opencv的实现 源地址:http://hi.baidu.com/superkiki1989/item/029f65013a128cd91ff0461b 这个是维基百科中的链接, ...
- 基于Opencv和Mfc的图像处理增强库GOCVHelper(索引)
GOCVHelper(GreenOpen Computer Version Helper )是我在这几年编写图像处理程序的过程中积累下来的函数库.主要是对Opencv的适当扩展和在实现Mfc程序时候的 ...
- 基于OpenCv的人脸检测、识别系统学习制作笔记之一
基于OpenCv从视频文件到摄像头的人脸检测 在OpenCv中读取视频文件和读取摄像头的的视频流然后在放在一个窗口中显示结果其实是类似的一个实现过程. 先创建一个指向CvCapture结构的指针 Cv ...
- 基于opencv网络摄像头在ubuntu下的视频获取
基于opencv网络摄像头在ubuntu下的视频获取 1 工具 原料 平台 :UBUNTU12.04 安装库 Opencv-2.3 2 安装编译运行步骤 安装编译opencv-2.3 参 ...
- 基于opencv的小波变换
基于opencv的小波变换 提供函数DWT()和IDWT(),前者完成任意层次的小波变换,后者完成任意层次的小波逆变换.输入图像要求必须是单通道浮点图像,对图像大小也有要求(1层变换:w,h必须是2的 ...
- 基于opencv在摄像头ubuntu根据视频获取
基于opencv在摄像头ubuntu根据视频获取 1 工具 原料 平台 :UBUNTU12.04 安装库 Opencv-2.3 2 安装编译执行步骤 安装编译opencv-2.3 參考h ...
- OpenCV2学习笔记(十四):基于OpenCV卡通图片处理
得知OpenCV有一段时间.除了研究的各种算法的内容.除了从备用,据导游书籍和资料,尝试结合链接的图像处理算法和日常生活,第一桌面上(随着摄像头)完成了一系列的视频流处理功能.开发平台Qt5.3.2+ ...
随机推荐
- Ice php配置
1) Removed the php extension directories and recompiled apache/PHP2) Rebooted the machine.3) I remov ...
- docker镜像管理基础
[root@node01 ~]# docker pull quay.io/coreos/flannel:v0.10.0-amd64 v0.10.0-amd64: Pulling from coreos ...
- BZOJ_3744_Gty的妹子序列
BZOJ3744: Gty的妹子序列 https://lydsy.com/JudgeOnline/problem.php?id=3744 分析: 预处理出来每一块块首到所有位置的逆序对数. 查询时主席 ...
- SHOI2001化工厂装箱员——记忆化搜索
题目:https://www.luogu.org/problemnew/show/P2530 太弱了不会用DP,于是暴搜: 每次传进一个数组c记录当前状态各种物品有多少个,枚举取哪种物品,返回最小值, ...
- JS---猜数字(0-100)
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8&quo ...
- 【opencv学习笔记三】opencv3.4.0数据类型解释
opencv提供了多种基本数据类型,我们这里分析集中常见的类型.opencv的数据类型定义可以在D:\Program Files\opencv340\opencv\build\include\open ...
- DataWindow.Net V2.5原始文件下载
DW2.5 原始安装程序下载 http://download.sybase.com/eval/datawindowNET_25_eval/CD50090-55-0250-01.zip
- NancyFX 第一章 NancyFX 简介
Nancy是.NET 平台的微框架.在受到Ruby社区的Sinatra框架启发下,NancyFx框架提供一个.NET平台下的低门槛.易上手的可用于Web开发工具包. 请注意我说的是可用于Web开发,这 ...
- JavaScript高级程序设计学习笔记第十四章--表单
1.在 HTML 中,表单是由<form>元素来表示的,而在 JavaScript 中,表单对应的则是 HTMLFormElement 类型. HTMLFormElement 继承了 HT ...
- [hdu2544]最短路spfa
解题关键:最短路模板一直没整理过,这里整理了一下spfa+链式前向星建图的最短路模板,以后网络赛省的打了. spfa算法的关键就是松弛操作,只有进行松弛操作,其后的点距离才可能被更新. #includ ...