在理解直方图均衡化的过程中,参考了一些书籍和博客,让人困惑的是,笔者对于直方图的理解还是停留在表面,并没有深入理解其内涵。因此,本文拟结合图片对直方图的概念进行阐述,并给出其Python实现,最后对她背后所蕴含的一些科学思维,谈谈自己的一些看法。

什么是直方图?

对于一副灰度图像I,她的每一个像素点I(x,y)都有一个灰度值,一般情况下可能的灰度取值有2^8=256个(0,1,...,255)。如果我们统计出灰度值r在I中出现的次数n,并对其进行归一化(n/N,N是所有灰度值出现次数的总和),这样我们就可以得到像素r在I中出现的概率p(r)。如果对每一个可能的灰度取值r都做同样的处理,我们可以得到如图1左侧所示的概率分布曲线,该曲线就是我们常说的直方图。

图1 直方图均衡化目标

什么是直方图均衡化?

通常情况下一副图像I的直方图如图1左侧所示,每一个灰度值r出现的概率不是相等的,这样会导致图像的一些细节信息不够突出,而直方图均衡化就是对灰度值r进行如下变换s=T(r),使得变换后的灰度分布如图1右侧所示(也就是说,每一个灰度值出现的概率是想同的),这样能够发现一些原先肉眼很难发现的细节,如图2所示(读者可以自己体会下)。说到这里,一般也就结束了,但是我们真的理解了吗?如何更好的理解呢?下面简要介绍一下笔者的理解方式。

假设我们有四个灰度级a,b,c,d,做个类比的话可以将她们理解为四个描述情感的词喜、怒、哀、乐。一般情况下我们得到的直方图可认为是p(a)=0.5,p(b)=0.5,p(c)=0,p(d)=0,而均衡化后的直方图是p(a)=0.25,p(b)=0.25,p(c)=0.25,p(d)=0.25. 如果我们以均衡化前的词描述人的情感则只有喜、怒,而均衡化后的词则有喜、怒、哀、乐。试问,哪种情形能够描述人更细微的情感变化呢?这也是笔者认为直方图均衡化之后能够描述更多图像细节的原因。

更进一步,如果一般情况下我们得到的直方图是p(a)=0.4,p(b)=0.4,p(c)=0.1,p(d)=0.1,那这按我们的理解意味什么呢?意味着大部分情况用喜、怒描述人的情感,而哀、乐几乎不用,当然了,如果能够自由运用喜、怒、哀、乐来描述人的情感是最好的哦。

图2 直方图均衡化示意图(左图变换前,右图变换后)

直方图均衡化的数学原理

笔者曾经是个数学控,总是认为凡事都应该从数学的基本原理出发,然而运用数学推理得出我们期望的结论。然而此刻,觉得自己的想法从根本上是错误的。下面以直方图均衡化数学原理为例进行说明。

我们直方图均衡化的目标如图1所示,那么怎么做到呢?这中间的约束条件又是什么呢(世上没有绝对的自由)?

可以设r原始图像灰度级,s均衡化后图像灰度级,不失一般性可以假设r的取值范围为[0,1]。那么什么是必须满足的约束条件呢?均衡化前后灰度级的意义不能变,也就是说变换前灰度级的含义是由黑到白,那么变换后也应该如此。此外,最好变换前后灰度级的取值范围一致。为使变换后的灰度仍保持从黑到白的单一变化顺序,且变换范围与原先一致,以避免整体变亮或变暗。必须规定:

(1)变换函数T(r)在r属于[0,1]范围内是单值、单调增函数;

(2)对于r属于[0,1],s=T(r)也属于[0,1]

图3 直方图均衡化原理示意图

这两条规定是满足我们均衡化要求的数学化描述(如果要应用数学的话,就应该将我们要求、目标等转化为数学语言进行描述)。

直方图均衡就是通过灰度变换函数s=T(r)将原图像直方图p (r)改变为均匀分布的直方图p(s)。由图3可知,在满足两条规定的前提下,因为s=T(r)(也就是说,r确定,s确定),结合概率论可知p (r)dr=p(s)ds又因为直方图均衡化后,有:p(s) = 1, s属于[0,1],因此,ds=p(r)dr。两边取积分有

这样我们就找到了s、r之间的映射关系。

直方图均衡化Python实现

由s、r之间的映射关系

可知,对于一副输入灰度图像I,我们首先计算其p(r),然后计算每一个灰度级r对应的

def histeq(img,nbr_bins=256):
""" Histogram equalization of a grayscale image. """

# 获取直方图p(r)
imhist, bins = histogram(img.flatten(), nbr_bins, normed = True)

# 获取T(r)
cdf = imhist.cumsum() # cumulative distribution function
cdf = 255 * cdf /cdf[-1] # 获取s,并用s替换原始图像对应的灰度值
result = interp(img.flatten(),bins[:-1],cdf) return result.reshape(img.shape),cdf

一些思考

笔者以前有这样一种误解:以为所有的理论都可以从基本的数学原理推导得出,于是在碰到新问题的时候,总是试图搞清楚各个数学公式的来源及其物理含义,而忽略了这些数学运作背后的目的是什么!这样的一个缺点就是,今天能够理解的理论,过了几天就不理解了。

现在笔者的一些体会是,如果按照以下思路理解问题,能够起到事半功倍的效果(有点夸张的成分在里面):首先搞清楚问题的来源、其次知晓解决问题的目的是什么、然后将问题数学化描述(时刻注意约束条件)、最后求解该数学问题。

总结:通常情况下,如果我们能够将前三个步骤走完,最后的求解问题通过借助于现有软件、算法,应该是水到渠成的事。(本人非数学专业,对怎么求解一个数学问题,通常只关心输入、输出、以及约束条件)

参考文献:

《Programming Computer Vision with Python》

图解直方图均衡化及其Python实现的更多相关文章

  1. 数学之路-python计算实战(14)-机器视觉-图像增强(直方图均衡化)

    我们来看一个灰度图像,让表示灰度出现的次数,这样图像中灰度为 的像素的出现概率是  是图像中全部的灰度数, 是图像中全部的像素数,  实际上是图像的直方图,归一化到 . 把  作为相应于  的累计概率 ...

  2. Python实现图像直方图均衡化算法

    title: "Python实现图像直方图均衡化算法" date: 2018-06-12T17:10:48+08:00 tags: [""] categorie ...

  3. 灰度图的直方图均衡化(Histogram Equalization)原理与 Python 实现

    原理 直方图均衡化是一种通过使用图像直方图,调整对比度的图像处理方法:通过对图像的强度(intensity)进行某种非线性变换,使得变换后的图像直方图为近似均匀分布,从而,达到提高图像对比度和增强图片 ...

  4. python——直方图均衡化

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

  5. python实现直方图均衡化,理想高通滤波与高斯低通滤波

    写在前面 HIT大三上学期视听觉信号处理课程中视觉部分的实验二,经过和学长们实验的对比发现每一级实验要求都不一样,因此这里标明了是2019年秋季学期的视觉实验二. 由于时间紧张,代码没有进行任何优化, ...

  6. 灰度直方图均衡化----python实现

    直方图均衡化是使用图像直方图进行对比度调整的图像处理的方法. 该方法通常会增加许多图像的整体对比度,尤其是当图像的可用数据由接近的对比度值表示时. 通过这种调整,强度可以更好地分布在直方图上. 这允许 ...

  7. OpenCV-Python教程(10、直方图均衡化)

    相比C++而言,Python适合做原型.本系列的文章介绍如何在Python中用OpenCV图形库,以及与C++调用相应OpenCV函数的不同之处.这篇文章介绍在Python中使用OpenCV和NumP ...

  8. 图像增强算法(直方图均衡化、拉普拉斯、Log、伽马变换)

    一.图像增强算法原理 图像增强算法常见于对图像的亮度.对比度.饱和度.色调等进行调节,增加其清晰度,减少噪点等.图像增强往往经过多个算法的组合,完成上述功能,比如图像去燥等同于低通滤波器,增加清晰度则 ...

  9. OpenCV计算机视觉学习(9)——图像直方图 & 直方图均衡化

    如果需要处理的原图及代码,请移步小编的GitHub地址 传送门:请点击我 如果点击有误:https://github.com/LeBron-Jian/ComputerVisionPractice 1, ...

随机推荐

  1. grub4dos

    default 1 timeout 5 gfxmenu (hd0,0)/grub/message configfile #####以上不在第一分区无法加载 title HITSZ_COMMAND co ...

  2. C#播放声音的四种方法 +AxWindowsMediaPlayer的详细用法

    C#播放声音的四种方法 第一种是利用DirectX 1.安装了DirectX SDK(有9个DLL文件).这里我们只用到MicroSoft.DirectX.dll和 Microsoft.Directx ...

  3. <工作一周的心情总结>

    到公司一个星期有余,明天就要周六了,蛮开心的,兴奋的今天下午没看一点代码,哈哈~ 我做的算是代码界里最简单,最好玩,最有成就感的html,web网页的编程. 截止到目前,除了看不懂的JavaScrip ...

  4. KNN算法——python实现

    二.Python实现 对于机器学习而已,Python需要额外安装三件宝,分别是Numpy,scipy和Matplotlib.前两者用于数值计算,后者用于画图.安装很简单,直接到各自的官网下载回来安装即 ...

  5. [转]CIDR简介

    IP Subnetting and Variable Length Subnet Masks Subnetting Basics 子网划分(subnetting)的优点: 1.减少网络流量 2.提高网 ...

  6. 使用nginx部署Yii 2.0\yii-advanced-app-2.0.6

    #user nobody; worker_processes 1; #error_log logs/error.log; #error_log logs/error.log notice; #erro ...

  7. Ejabberd作为推送服务的优化手段

    AVOS Cloud目前还在用Ejabberd做Android的消息推送服务.当时选择Ejabberd,是因为Ejabberd是一个发展很长时间的XMPP实现,并且基于Erlang,设想能在我们自主研 ...

  8. jquery的blur之后,focus获取不到焦点的解决办法

    一:很多童鞋可能会遇到这种情况: jquery的blur之后,focus获取不到焦点. 二:使用场景: 用户填写信息的时候,若邮箱为空,则提示 请填写邮箱,并将光标置于填写邮箱的文本框里,方便用户的再 ...

  9. Converter转换器使用

    package com.xu.javabean; import java.lang.reflect.InvocationTargetException; import java.util.Date; ...

  10. android studio 生成aar包并在其他工程引用 (导入)aar包

    1.aar包是Android studio下打包android工程中src.res.lib后生成的aar文件,aar包导入其他android studio 工程后,其他工程可以方便引用源码和资源文件 ...