经典去雾算法-何凯明09年提出暗通道先验去雾(Single Image Haze Removal Using Dark Channel Prior)

暗通道去雾公式:I(x) = f(x)*t(x) + (1 – t(x))*A

I(x)为待去雾图像,f(x)为去雾后图像,t(x)为透射率(0,1),A为大气光成分。

根据公式,去雾算法可解释为:有雾时,相机获取到的图像为两部分组成,一部分为被拍摄物体发射光线穿过雾霾后的光线,另一部分为大气光被雾霾反射后的光线。被拍摄物体发射光线f(x)通过雾霾,雾霾透射率为t(x),那么被摄物体光线到达相机后值为 f(x)*t(x)。原始大气光值为A,大气光的方向可看做与被拍摄物体光线完全相反,大气光一部分穿过雾霾,一部分被雾霾反射,被反射后的光线值即为A - A*t(x))。

整个去雾流程如下图:

有了算法模型,接下来对各个部分进行细化实现,首先计算透射率。暗通道先验法指出,根据大量图像统计,无雾图像RGB通道总有一个通道值趋近于0,也就是说在该像素上透射率t(x)趋近于1,f(x)与I(x)几乎相等。而有雾图像,由于雾霾反射的大气光干扰,RGB通道上的最低值,也就是被反射后的大气光值,通过这个值即可计算出该像素上的透射率,当然实际情况下需要考虑其他因素造成的干扰,一般情况下需要对原始图像通过RGB最低值计算的灰度图进行最低值滤波,根据某个像素相邻范围的最低值计算透射率。

整个计算透射率过程分为三个步骤:第一步为原始图像通过RGB最低值转灰度图;第二步对灰度图进行最低通道滤波,滤波器半径可选,取滤波器内最低值作为中心像素值;第三部对低通滤波后的灰度图进行高斯低通滤波,主要作用为平滑图像,让边缘过度平缓。

透射率计算流程如下:

计算大气光成分值则比较简单,大气光成分A可以看做一个独立的RGB像素,包含三个值。一般是对原始图像RGB通道统计0~255概率分布,分别从各个通道最大值开始取占比大于万分之一的值作为A中对应值。

完成透射率和大气光成分计算后,接下来就是根据公式计算去雾图像。实际上还需要计算透射率图像,透射率图像通过高斯低通滤波后图像进行反转得到,在实际应用开发上,这一步可以省略,直接通过滤波后灰度图实际上可以看做雾霾反射率图T(x),那么透射率即t(x)=1-T(x)。去雾处理后的图像一般会比较暗,可以通过自动对比度或自动色阶进行优化。

基于暗通道的去雾对于浓度不均匀的雾霾去雾效果比较好,但计算透射率过程由于最低值滤波和高斯低通滤波随着卷积核增大,消耗计算量也越大,处理单张影像还好,如果用于批量处理影像,显然不太实用。当然在实际应用中,可以考虑减少滤波核半径,牺牲一些效果,提升处理速度。把最低值通滤波和高斯低通滤波核半径都设置为1进行测试。

测试图像:

去雾效果图:

附上代码,java版的实现:

package tools;import java.awt.image.BufferedImage;
import java.util.ArrayList;
import java.util.List;public class AutoHazeRemoval {//自动去雾public BufferedImage hazeRemoval(BufferedImage image) {BufferedImage tempImage = new BufferedImage(image.getWidth(), image.getHeight(), image.getType());BufferedImage grayImage = new ImageGray().transferGrayImageByLowest(image);grayImage = new LowestFilter().lowestFilter(grayImage, 1);grayImage = new GaussianBlur().gaussBlur(grayImage, 1, 1);int[] A = extractA(image);for (int i = 0; i < image.getWidth(); i++) {for (int j = 0; j < image.getHeight(); j++) {int rgb = image.getRGB(i, j);double R = (rgb >> 16) & 0xff;double G = (rgb >> 8) & 0xff;double B = rgb & 0xff;//计算透射率int transmissionValue = grayImage.getRGB(i, j) & 0xff;double transmission = 0.95 * (double)transmissionValue / 255;R = (R - A[0] * transmission) / (1 - transmission); G = (G - A[1] * transmission) / (1 - transmission); B = (B - A[2] * transmission) / (1 - transmission); rgb = (255 & 0xff) << 24 | (clamp((int)R) & 0xff) << 16| (clamp((int)G) & 0xff) << 8 | (clamp((int)B) & 0xff);tempImage.setRGB(i, j, rgb);}}return tempImage;}/*** 通过RGB在0~255频率分布计算全局大气光成分* * @param image* @return*/public int[] extractA(BufferedImage image) {List<Integer[]> list = generateBinary(image);int[] result = new int[3];result[0] = getValue(image,list.get(0));result[1] = getValue(image,list.get(1));result[2] = getValue(image,list.get(2));return result;}private int getValue(BufferedImage image,Integer[] list) {double temp = 0.0;int result = 0;for(int i = 255; i > 0; i--) {double num = list[i] / (double)(image.getWidth()*image.getHeight());temp += num;if (temp >= 0.0001) {result = i;break;}}return result;}/*** 图像二值化 计算图像RGB值从0~255之间分布* * @return*/public List<Integer[]> generateBinary(BufferedImage image) {List<Integer[]> list = new ArrayList<>();Integer[] rlist = new Integer[256];Integer[] glist = new Integer[256];Integer[] blist = new Integer[256];// 通过循环,往集合里面填充0~255个位置,初始值都为0for (int i = 0; i < 256; i++) {rlist[i] = 0;glist[i] = 0;blist[i] = 0;}for (int i = 0; i < image.getWidth(); i++) {for (int j = 0; j < image.getHeight(); j++) {int rgb = image.getRGB(i, j);int r = (rgb >> 16) & 0xff;int g = (rgb >> 8) & 0xff;int b = rgb & 0xff;rlist[r] = rlist[r] + 1;glist[g] = rlist[g] + 1;blist[b] = rlist[b] + 1;}}list.add(rlist);list.add(glist);list.add(blist);return list;}// 判断a,r,g,b值,大于256返回256,小于0则返回0,0到256之间则直接返回原始值private int clamp(int rgb) {if (rgb > 255)return 255;if (rgb < 0)return 0;return rgb;}
}

暗通道先验去雾实现过程分析相关推荐

  1. [Python图像识别] 四十六.图像预处理之图像去雾详解(ACE算法和暗通道先验去雾算法)

    该系列文章是讲解Python OpenCV图像处理知识,前期主要讲解图像入门.OpenCV基础用法,中期讲解图像处理的各种算法,包括图像锐化算子.图像增强技术.图像分割等,后期结合深度学习研究图像识别 ...

  2. 基于导向滤波的暗通道先验去雾算法(Python,可直接运行)

    基于导向滤波的暗通道先验去雾算法(Python语言,可直接运行) 1 编译环境 2 原理介绍 2.1 暗通道先验 2.1.1 暗通道先验理论与去雾模型 2.1.2 处理步骤 2.2 导向滤波求t(x) ...

  3. 图像去雾算法--暗通道先验去雾算法

    图像去雾: 在雾天拍摄的图像容易受雾或霾的影响,导致图片细节模糊.对比度低以至于丢失图像重要信息,为解决此类问题图像去雾算法应运而生.图像去雾算法是以满足特定场景需求.突出图片细节并增强图片质量为目的 ...

  4. 暗通道先验去雾算法介绍及其几何意义的解释过程

    何恺明的暗通道先验(dark channel prior)去雾算法是CV界去雾领域很有名的算法,关于该算法的论文"Single Image Haze Removal Using Dark C ...

  5. 从暗通道先验去雾到海底图像修复-三维重建辅助计算摄影

    点击上方"小白学视觉",选择加"星标"或"置顶"重磅干货,第一时间送达 一. Sea Thru:海底图像修复 我想很多朋友一定看过海底的各种 ...

  6. 50. 从暗通道先验去雾到海底图像修复-三维重建辅助计算摄影

    点击上方"小白学视觉",选择加"星标"或"置顶" 重磅干货,第一时间送达推荐阅读 42个pycharm使用技巧,瞬间从黑铁变王者Google ...

  7. 关于暗通道先验去雾问题的小结

    前段日子导师甩给我一篇何博士的论文,叫做<Single Image Haze Removal Using Dark Channel Prior>,利用统计得来的暗通道先验实现对有雾图像的去 ...

  8. 基于OpenCV实现暗通道先验去雾算法及改进,效果惊人

    ❤️欢迎订阅<从实战学python>专栏,用python实现爬虫.办公自动化.数据可视化.人工智能等各个方向的实战案例,有趣又有用!❤️ 更多精品专栏简介点这里 治愈生活的良方 就是保持对 ...

  9. Matlab:单幅图象的暗原色先验去雾改进算法,能够很好地改进天空或明亮部分色彩失真问题

    Matlab:单幅图象的暗原色先验去雾改进算法,能够很好地改进天空或明亮部分色彩失真问题 目录 输出结果 实现代码 代码下载 输出结果 实现代码 %单幅图象的暗原色先验去雾改进算法,能够很好地改进天空 ...

最新文章

  1. CTF大赛学习第一天!!!(学习中)
  2. 基于表达式的访问控制
  3. layui 表格点击图片放大
  4. Java毕设项目:垃圾分类(带源码和搭建过程)
  5. C# 调用命令行,参数有空格
  6. AppWeb或云打分时,附加分相关问题
  7. fd抓包数据类型_fd抓包教程 FD入门简介(配置教程) fd视频教程2016
  8. VMware16下载与安装
  9. html格式蠕虫病毒,蠕虫病毒Win32.Womble.B
  10. 123457123456#0#-----com.yuming.FromPuzzleGame01--前拼后广--宝宝农场拼图cym
  11. 时间服务器端口协议,时间服务器端口
  12. 张艺谋说高仓健:一位古代君子
  13. DRC(Data Replicate Center)
  14. iPhone X Face ID判断
  15. 关于期刊审稿与同行评审,论文“不为所知”的拒稿秘密在这里
  16. 联发科MT5592数字电视DTV芯片处理器参数介绍
  17. 制药企业计算机系统urs,制药设备urs.pdf
  18. 品城记探店之鹭江滨江东路丘大6仔记餐厅
  19. 沪深A股分析数据龙虎榜信息API接口(JSON标准格式,Get请求方式)
  20. java 如何使用ocr_Java使用tess4J进行OCR图像识别

热门文章

  1. 算法训练营12-动态规划
  2. hdu 4585 Shaolin set
  3. 38行代码AC——L1-025 正整数A+B (15分)(~解题报告~)
  4. 15行代码AC——ZOJ - 4118 Stones in the Bucket(思维题+优化方案)(第十届山东省ACM程序设计竞赛F题)
  5. Spring容器创建过程
  6. 计算机网络实验(华为eNSP模拟器)——第六章 密码模式和AAA模式
  7. Select的OnChange()事件中获取选中的值
  8. MiniGUI+qvfb+Eclipse完成嵌入式系统图形开发(开发环境的搭建)
  9. python中如何输出中文_python中怎么输出中文-问答-阿里云开发者社区-阿里云
  10. python商城源码_腾讯大佬用了12小时讲完的Python,整整400集,拿走不谢