直方图均衡化

直方图均衡化(Histogram Equalization)是直方图最典型的应用,是图像点运算的一种。对于一幅输入图像,通过运算产生一幅输出图像,点运算是指输出图像的每个像素点的灰度值由输入像素点决定,即:

直方图均衡化是通过灰度变换将一幅图像转换为另一幅具有均衡直方图,即在每个灰度级上都具有相同的象素点数过程。从分布图上的理解就是希望原始图像中y轴的值在新的分布中尽可能的展开。变换过程是利用累积分布函数对原始分布进行映射,生成新的均匀拉伸的分布。因此对应每个点的操作是寻找原始分布中y值在均匀分布中的位置,如下图是理想的单纯高斯分布映射的示意图:

(图片来源:《Learnning OpenCV》 p189)

OpenCV中的cvEqualizeHist

OpenCV中有灰度直方图均衡化的函数cvEqualizeHist,接口很明朗:

[cpp] view plaincopy
  1. void cvEqualizeHist( const CvArr* src, CvArr* dst );

注意此函数只能处理单通道的灰色图像,对于彩色图像,我们可以把每个信道分别均衡化,再Merge为彩色图像。

实践:图像直方图均衡化

[cpp] view plaincopy
  1. int main()
  2. {
  3. IplImage * image= cvLoadImage("baboon.jpg");
  4. //显示原图及直方图
  5. myShowHist("Source",image);
  6. IplImage* eqlimage=cvCreateImage(cvGetSize(image),image->depth,3);
  7. //分别均衡化每个信道
  8. IplImage* redImage=cvCreateImage(cvGetSize(image),image->depth,1);
  9. IplImage* greenImage=cvCreateImage(cvGetSize(image),image->depth,1);
  10. IplImage* blueImage=cvCreateImage(cvGetSize(image),image->depth,1);
  11. cvSplit(image,blueImage,greenImage,redImage,NULL);
  12. cvEqualizeHist(redImage,redImage);
  13. cvEqualizeHist(greenImage,greenImage);
  14. cvEqualizeHist(blueImage,blueImage);
  15. //均衡化后的图像
  16. cvMerge(blueImage,greenImage,redImage,NULL,eqlimage);
  17. myShowHist("Equalized",eqlimage);
  18. }

原始图像及灰度直方图如下:

均衡化后的直方图:

直方图匹配

直方图匹配又叫直方图规定化(Histogram Normalization/Matching)是指对一副图像进行变换,使其直方图与另一幅图像的直方图或特定函数形式的直方图进行匹配。应用场景如不同光照条件下的两幅图像,我们可以在比较两幅图像前先进行匹配变化。

参考shlkl99上传的直方图匹配代码,将图像规定化为高斯分布函数。

[cpp] view plaincopy
  1. //将图像与特定函数分布histv[]匹配
  2. void myHistMatch(IplImage *img,double histv[])
  3. {
  4. int bins = 256;
  5. int sizes[] = {bins};
  6. CvHistogram *hist = cvCreateHist(1,sizes,CV_HIST_ARRAY);
  7. cvCalcHist(&img,hist);
  8. cvNormalizeHist(hist,1);
  9. double val_1 = 0.0;
  10. double val_2 = 0.0;
  11. uchar T[256] = {0};
  12. double S[256] = {0};
  13. double G[256] = {0};
  14. for (int index = 0; index<256; ++index)
  15. {
  16. val_1 += cvQueryHistValue_1D(hist,index);
  17. val_2 += histv[index];
  18. G[index] = val_2;
  19. S[index] = val_1;
  20. }
  21. double min_val = 0.0;
  22. int PG = 0;
  23. for ( int i = 0; i<256; ++i)
  24. {
  25. min_val = 1.0;
  26. for(int j = 0;j<256; ++j)
  27. {
  28. if( (G[j] - S[i]) < min_val && (G[j] - S[i]) >= 0)
  29. {
  30. min_val = (G[j] - S[i]);
  31. PG = j;
  32. }
  33. }
  34. T[i] = (uchar)PG;
  35. }
  36. uchar *p = NULL;
  37. for (int x = 0; x<img->height;++x)
  38. {
  39. p = (uchar*)(img->imageData + img->widthStep*x);
  40. for (int y = 0; y<img->width;++y)
  41. {
  42. p[y] = T[p[y]];
  43. }
  44. }
  45. }
  46. // 生成高斯分布
  47. void GenerateGaussModel(double model[])
  48. {
  49. double m1,m2,sigma1,sigma2,A1,A2,K;
  50. m1 = 0.15;
  51. m2 = 0.75;
  52. sigma1 = 0.05;
  53. sigma2 = 0.05;
  54. A1 = 1;
  55. A2 = 0.07;
  56. K = 0.002;
  57. double c1 = A1*(1.0/(sqrt(2*CV_PI))*sigma1);
  58. double k1 = 2*sigma1*sigma1;
  59. double c2 = A2*(1.0/(sqrt(2*CV_PI))*sigma2);
  60. double k2 = 2*sigma2*sigma2;
  61. double p = 0.0,val= 0.0,z = 0.0;
  62. for (int zt = 0;zt < 256;++zt)
  63. {
  64. val = K + c1*exp(-(z-m1)*(z-m1)/k1) + c2*exp(-(z-m2)*(z-m2)/k2);
  65. model[zt] = val;
  66. p = p +val;
  67. z = z + 1.0/256;
  68. }
  69. for (int i = 0;i<256; ++i)
  70. {
  71. model[i] = model[i]/p;
  72. }
  73. }

实践:直方图匹配

对示例图片每个信道分别进行匹配处理

对比直方图

OpenCV中提供了cvCompareHist函数用以对比两个直方图的相似度:
[cpp] view plaincopy
  1. double cvCompareHist(
  2. const CvHistogram* hist1, //直方图1
  3. const CvHistogram* hist2, //直方图2
  4. int method//对比方法
  5. );

method有CV_COMP_CORREL, CV_COMP_CHISQR,CV_COMP_INTERSECT,CV_COMP_BHATTACHARYYA四种方法,对应公式如下:

实践:对比不同光照条件的两幅图像直方图

直方图的对比主要用以判断两幅图像的匹配度,我们试验以下两幅图像直方图对比的结果:

      
[cpp] view plaincopy
  1. int main()
  2. {
  3. IplImage * image= cvLoadImage("myhand1.jpg");
  4. IplImage * image2= cvLoadImage("myhand2.jpg");
  5. int hist_size=256;
  6. float range[] = {0,255};
  7. float* ranges[]={range};
  8. IplImage* gray_plane = cvCreateImage(cvGetSize(image),8,1);
  9. cvCvtColor(image,gray_plane,CV_BGR2GRAY);
  10. CvHistogram* gray_hist = cvCreateHist(1,&hist_size,CV_HIST_ARRAY,ranges,1);
  11. cvCalcHist(&gray_plane,gray_hist,0,0);
  12. IplImage* gray_plane2 = cvCreateImage(cvGetSize(image2),8,1);
  13. cvCvtColor(image2,gray_plane2,CV_BGR2GRAY);
  14. CvHistogram* gray_hist2 = cvCreateHist(1,&hist_size,CV_HIST_ARRAY,ranges,1);
  15. cvCalcHist(&gray_plane2,gray_hist2,0,0);
  16. //相关:CV_COMP_CORREL
  17. //卡方:CV_COMP_CHISQR
  18. //直方图相交:CV_COMP_INTERSECT
  19. //Bhattacharyya距离:CV_COMP_BHATTACHARYYA
  20. double  com=cvCompareHist(gray_hist,gray_hist2,CV_COMP_BHATTACHARYYA);
  21. cout<<com<<endl;
  22. }

输出结果为:0.396814

cvCompareHist的结果为【0,1】的浮点数,越小表示两幅图匹配度越高,0.0时两幅图精确匹配。(可以试验两幅完全一样的图即为0.0)。
针对上面两幅图,我们分别先进行直方图匹配变化:
之后使用cvCompareHist()对比两幅图像的直方图,输出结果为0.267421

表明两幅图的匹配度变高了。
注意method用不同的方法对比结果是不同的。

应用

通过对比我们可以设置EMD的阈值来判定皮肤或手的ROI。《Learnning OpenCV》后面有相应的练习题:收集手的肤色直方图,对比室内,室外手的直方图的EMD距离,利用这些测量值设置一个距离阈值。
a.利用该阈值检测第三幅图(如室外阴影),看能能否很好的检测肤色直方图。
b.随机选择不是肤色的背景块直方图,观测EMD变化,试验与真实肤色对比时能否很好的拒绝背景。
如上也即是直方图对比可以应用的场景。

实验代码下载:http://download.csdn.net/detail/xiaowei_cqu/4332914

直方图应用:直方图均衡化,直方图匹配,对比直方图相关推荐

  1. 【OpenCV】直方图应用:直方图均衡化,直方图匹配,对比直方图

    本文链接:https://blog.csdn.net/xiaowei_cqu/article/details/7606607                                       ...

  2. 学习笔记(二)——直方图均衡化和匹配

    本文为原创作品,转载请注明出处 欢迎关注我的博客:http://blog.csdn.net/hit2015spring和http://www.cnblogs.com/xujianqing/ 作者: 晨 ...

  3. 【opencv】(7) 图像匹配、直方图、图像均衡化

    各位同学好,今天和大家分享一下opencv中图像匹配方法,和图像均衡化方法 (1)模板匹配: cv2.matchTemplate():(2)图像直方图: cv2.calcHist():(3)图像均衡化 ...

  4. 图像灰度直方图匹配(直方图规定化,Histogram Matching)实验

    一.使用相同图像,不同灰度分布做匹配 matlab代码: %% 两张图片histmatch,直方图均衡后match原图 clc;close all;clear all ImgIn=rgb2gray(i ...

  5. OpenCv:直方图均衡化(HE),自适应直方图均衡化(AHE),限制对比度自适应直方图均衡化(CLAHE)

    总结了使用Python OpenCv处理图像直方图均衡化(HE),自适应直方图均衡化(AHE),限制对比度自适应直方图均衡化(CLAHE)的方法. 目录 直方图均衡化(HE) 自适应直方图均衡化(AH ...

  6. OpenCV学习——直方图、边缘检测、模板匹配以及霍夫变化

    OpenCV学习--直方图.边缘检测.模板匹配以及霍夫变化 OpenCV学习--直方图.边缘检测.模板匹配以及霍夫变化 直方图 图像直方图 直方图的术语和意义 掩膜的应用 直方图均衡化 自适应的直方图 ...

  7. python统计图像灰度直方图_python 对一幅灰度图像进行直方图均衡化

    from PIL import Image from pylab import * from numpy import * def histeq(im,nbr_bins = 256): "& ...

  8. 线性变换,分段线性变换,伽马变换,直方图正规化,直方图均衡化,局部自适应直方图均衡化的原理以及python代码

    1.基础概念 1.1 图像灰度直方图 灰度直方图是图像灰度级的函数,用来描述每个灰度级在图像矩阵中的像素个数或者占有率.图像的对比度是通过灰度级范围来度量的,而灰度级范围可通过观察灰度直方图得到,灰度 ...

  9. python 灰度直方图_数字图像处理灰度变换之灰度直方图及python实现

    图像灰度直方图 灰度直方图是图像灰度级的函数,用来描述每个灰度级在图像矩阵中的像素个数或者占有率.直方图显示图像数据时会以左暗右亮的分布曲线形式呈现出来.横坐标是灰度级,纵坐标是该灰度级出现的频率.图 ...

最新文章

  1. 国产项目管理软件/敏捷开发工具
  2. Android-使用AIDL进程间通信
  3. HTTP协议通信原理
  4. 有状态服务和无状态服务的区别与联系
  5. mac 安装使用 webp 来压缩图片
  6. 利用jquery的ajax获取后台返回的json数据为空
  7. 二元偏导数存在的条件_偏导数连续怎么证明
  8. java工程师中兴面试题
  9. CatBoost快速入门
  10. mysql 文本类型的长度
  11. html公历农历相互转换,JavaScript实现公历转换农历
  12. Android 切换双卡数据链接__2019.11.22
  13. c语言编译kbhit出现问题,在VC++中运行出现error C2065: 'kbhit' : undeclared identifier,什么意思?怎么调试?...
  14. 区块链现在的样子:当年的DOS操作系统
  15. C++动态分配内存空间
  16. Linux入门——1、Linux的安装(Ubuntu)
  17. win7计算机无法识别分辨率,win7系统无法调整分辨率显示灰色的详细方案
  18. 研究称开放式办公布局对大脑有害 转载和评论
  19. Dell戴尔Inspiron 1440 驱动下载XP
  20. 结对编程项目:带UI的小初高数学学习软件——感想及领悟

热门文章

  1. 机器学习入门系列四(关键词:BP神经网络)
  2. 让餐厅放心的云服务-雅座CRM技术解密
  3. Java在游戏服务器开发中的应用
  4. 每日一博 - 常见的Spring事务失效事务不回滚案例集锦
  5. Spring5源码 - 13 Spring事件监听机制_@EventListener源码解析
  6. Oracle 不使用DBCA在Oracle 11中删除数据库
  7. AS插件-Android Parcelable code generator.
  8. python 合并排序的数组
  9. tensorflow对应的python版本_详解Tensorflow不同版本要求与CUDA及CUDNN版本对应关系
  10. 破解IDEA2018的正确姿势