数字图像处理之直方图均衡化
2015-07-18 11:11
429 查看
以下例子源自《数字图像处理》第三版
r表示待处理图像的灰度,取值区间[0,L-1]。r=0表示黑色,r= L-1表示白色。输出灰度值s,变换形式:
s = T(r) ,0<=r<=L-1。
离散变换形式
sk = T(rk) = (L-1)(pr0+pr1+...+prk) ,pr为像素值的概率密度。
= (L-1)(n0+n1+...+nk)/MN,n为每个像素值对于的个数,M、N为图像行和列数。
笔者采用c++语言,编写了直方图均衡化处理的类,并用opencv绘制了均衡化前后的统计直方图,以及通过直方图均衡化的原图像。
类的头文件代码如下:
最后写了测试函数test.cpp,代码如下:
结果如图:
原图直方图
![](http://img.blog.csdn.net/20150718120317871?watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQv/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/Center)
均衡化后直方图
![](http://img.blog.csdn.net/20150718120400986?watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQv/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/Center)
原图像(出自冈萨雷斯第三版)
![](http://img.blog.csdn.net/20150718120446150?watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQv/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/Center)
直方图均衡化后的图:
![](http://img.blog.csdn.net/20150718120521318?watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQv/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/Center)
版权声明:本文为博主原创文章,未经博主允许不得转载。
r表示待处理图像的灰度,取值区间[0,L-1]。r=0表示黑色,r= L-1表示白色。输出灰度值s,变换形式:
s = T(r) ,0<=r<=L-1。
离散变换形式
sk = T(rk) = (L-1)(pr0+pr1+...+prk) ,pr为像素值的概率密度。
= (L-1)(n0+n1+...+nk)/MN,n为每个像素值对于的个数,M、N为图像行和列数。
笔者采用c++语言,编写了直方图均衡化处理的类,并用opencv绘制了均衡化前后的统计直方图,以及通过直方图均衡化的原图像。
类的头文件代码如下:
//<span style="font-family: Arial, Helvetica, sans-serif;">histogramEqualization.h</span>
#ifndef _HIS_E_ #define _HIS_E_ class hisEqt { public: hisEqt::hisEqt(); hisEqt::~hisEqt(); public: int w ; int h; int nlen; int *pHis; float *pdf; //=====求像素分布概率密度==== void getPdf(); //======统计像素个数======= void getHis(unsigned char*imgdata); //==========画统计分布直方图=============== //void drawHistogram(const float*pdf,Mat &hist1); //===========直方图均衡化========== void hisBal(); //====直方图均衡化后的图像=== void imgBal(unsigned char* img); }; #endif类源文件:
#include <iostream> #include "histogramEqualization.h" using namespace std; hisEqt::hisEqt():nlen(0){ pHis = new int[256*sizeof(int)]; memset(pHis,0,256*sizeof(int)); pdf = new float[255*sizeof(float)]; memset(pdf,0,255*sizeof(float)); } hisEqt::~hisEqt(){ delete []pHis; delete []pdf; } //======统计像素个数======= void hisEqt::getHis(unsigned char*imgdata){ for (int i =0;i<nlen;i++) { pHis[imgdata[i]]++; } } //=====求像素分布概率密度==== void hisEqt:: getPdf(){ for(int k =0;k<256;k++) { pdf[k] = pHis[k]/float(nlen); } } //===========直方图均衡化========== void hisEqt::hisBal(){ for(int k =1;k<256;k++) { pdf[k] += pdf[k-1]; } for(int k =0;k<256;k++) { pHis[k] = 255*pdf[k]; } } //====直方图均衡化 void hisEqt:: imgBal(unsigned char* img){ for (int i =0;i<nlen;i++) { img[i] = pHis[img[i]]; } }
最后写了测试函数test.cpp,代码如下:
#include <opencv2/opencv.hpp> #include "histogramEqualization.h" using namespace cv; void drawHistogram(const float*pdf,Mat& hist1); int main() { Mat image = imread("Fig0308(a)(pollen).tif"); if (!image.data) { return -1; } Mat hist2(256,256,CV_8UC3,Scalar(0,0,0)); Mat hist1(256,256,CV_8UC3,Scalar(0,0,0)); Mat imgOut = Mat(image.rows,image.cols,CV_8UC3,Scalar(0,0,0)); vector<Mat> planes; int chn = image.channels(); if (chn==3) { split(image,planes); } while (chn) { chn--; unsigned char* imageData = new unsigned char[sizeof(unsigned char)*(image.cols*image.rows)]; memcpy(imageData,planes[chn].data,planes[chn].cols*planes[chn].rows); hisEqt his; his.nlen = image.rows*image.cols; his.getHis(imageData); his.getPdf(); // //======画原图直方图并保存============ drawHistogram(his.pdf,hist1); imwrite("hisline.jpg",hist1); his.hisBal(); his.getPdf(); // //======画均衡化后直方图并保存============ drawHistogram(his.pdf,hist2); imwrite("his_balanceline.jpg",hist2); // //=====图像均衡化=== his.imgBal(imageData); memcpy(planes[chn].data,imageData,planes[chn].cols*planes[chn].rows); imageData = NULL; delete[] imageData; } //merge(planes0,imgOut); merge(planes,image); imwrite("result.jpg",image); } void drawHistogram(const float *pdf,Mat& hist1){ for(int k =0;k<256;k++) { /*if (k>0) { Point a(k-1,255-pdf[k-1]*2550),b(k,255-pdf[k]*2550); line( hist1, a, b, Scalar( 0, 0, 255 ), 2); }*/ if (k%2==0) { Point a(k,255),b(k,255-pdf[k]*2550); line( hist1, a, b, Scalar( 0, 0, 255 ), 1); } else { Point a(k,255),b(k,255-pdf[k]*2550); line( hist1, a, b, Scalar( 0, 255, 0 ), 1); } } }
结果如图:
原图直方图
均衡化后直方图
原图像(出自冈萨雷斯第三版)
直方图均衡化后的图:
转载请注明出处:http://write.blog.csdn.net/postedit/46940805
实验代码下载:http://download.csdn.net/my
版权声明:本文为博主原创文章,未经博主允许不得转载。
相关文章推荐
- 实时更新相关专利研究
- for循环和jquery的each()跳出循环的方法
- 同时安装使用Python 2.X和 Python 3.X
- poj1548Robots dfs实践
- UVA494判断一个字符串中单词的个数
- [刷题]Space Replacement
- 黑白图像
- request.getParameter(param) 的中文乱码问题
- [译]用R语言做挖掘数据《四》
- Android--百分比布局库(percent-support-lib)
- 3162 抄书问题
- 类和对象
- 禁止浏览器中双击选中元素的解决方法
- 数据库之函数、数据类型转换
- git 常用场景的命令
- 各种排序算法的比较
- leetcode 76: Minimum Window Substring
- 【bzoj1509】 NOI2003 逃学的小孩 树的直径
- c++课程设计——————银行系统
- The Unsolvable Problem