用OpenCV4实现图像的超分别率

本实验原文链接:·

https://arxiv.org/pdf/1807.06779.pdf

原文摘要

单图像超分辨率(SISR)的主要挑战是如何恢复微小纹理等高频细节。然而,大多数最先进的方法缺乏识别高频区域的特定模块,导致输出图像模糊。本文提出了一种基于注意的方法来区分纹理区域和平滑区域。高频细节定位后,进行高频补偿。这种方法可以与先前提出的SISR网络相结合。通过提供高频增强,可以获得更好的性能和视觉效果。本文还提出了自己的由DenseRes块组成的SISR网络。该模块提供了一种将低层特征和高层特征相结合的有效方法。大量的基准测试表明,本文提出的方法比SISR的最新作品有了显著的改进。

单图像超分辨率(SISR)的任务是从单低分辨率(LR)输入图像中推断出高分辨率(HR)图像。

这是一个高度不适定的问题,因为在低通滤波和下采样过程中,诸如微小纹理等高频信息会丢失。因此,SISR是一对多的映射,本文的任务是找到最合理的图像,尽可能地恢复微小的纹理。为了从LR图像中恢复HR图像,需要大的接收场从LR图像中获取更多的上下文信息。使用更深层的网络是增加接受视野的更好方法。深度网络的一个缺点是梯度问题的消失,使得网络难以训练。Heetal.[1]利用这些学习框架来进行网络训练。跳过连接是另一种通过网络增加梯度和信息流动的解决方案。低层特征包含了有效的信息,可以用来重建HR图像。SISR将从不同层次的集体信息中获益。SISR的难点在于恢复高频细节,如微小纹理。

输出图像与原始图像之间的均方误差(MSE)常作为损失函数来训练卷积神经网络。然而,在追求高峰值信噪比(PSNR)的过程中,MSE会返回许多可能解的均值,从而使输出图像变得模糊和不可信。为了恢复高频细节,人们提出了知觉损失[2],它鼓励生成特征表示相似的图像的网络,从而产生更清晰的图像。莱迪格在阿尔。[3] ,[4]结合对抗性网络、感知损失和纹理损失,鼓励输出图像恢复微小纹理等高频细节。但是所有这些网络并不清楚高频细节的位置,它们只是试图盲目地恢复

纹理。因此,这些网络的性能并不令人满意。为了解决这些问题,首先,在denseNet[5]的基础上,本文提出了一种新的由剩余积木块(Resblock)[1]组成的DenseRes块。每个Resblock的输出都连接到其他Resblock,增强了信息的流动性,避免了冗余特征的重新学习。利用DenseRes块,减少了梯度消失问题,网络易于训练。第二,本文提供一个注意机制来处理高频细节的恢复。受用于语义像素级分割的U-net[6]的启发,本文提出了一种新的混合密集连接U-net,以帮助网络区分是否存在需要修复或类似于插值图像的细小纹理区域。它作为一个特征选择器,有选择地增强高频特征。因此,可以尽可能接近地恢复纹理。这是第一次将注意机制引入SISR。方法简单有效。通过选择性地提供高频增强,它缓解了输出图像容易模糊的问题。注意机制可以与先前提出的SISR网络相结合。获得了较高的信噪比和信噪比。另一个贡献是本文提出了DenseRes块,它提供了一种有效的方法来结合低层特征和高层特征。这有利于恢复高频细节。本文在四个公开的基准数据集上评估本文的模型。它在PSNR和结构相似性(SSIM)指数方面优于当前最新的方法。PSNR比VDSR[7]和DRCN[8]分别提高了0.54db和0.52dB。

图像超像素

传统方式的图像超像素常见的方式就是基于立方插值跟金字塔重建。OpenCV中对这两种方式均有实现,低像素图像在纹理细节方面很难恢复,从低像素图像到高像素图像是典型的一对多映射,如果找到一种好的映射关系可以尽可能多的恢复或者保留图像纹理细节是图像超像素重建的难点之一,传统方式多数都是基于可推导的模型实现。而基于深度学习的超像素重新方式过程未知但是结果优于传统方式。在深度学习方式的超像素重建中,对低像素图像采样大感受野来获取更多的纹理特征信息。OpenVINO中提供的单张图像超像素网络参考了下面这篇文章

该网络模型主要分为两个部分

·       特征重建网络,实现从低分辨率到高分辨率的像素重建

·       注意力生成网络,主要实现图像中高频信息的修复

通过两个网络的的输出相乘,还可以得到高分辨率图像的残差。特征重建网络主要包括三个部分。卷积层实现特征提取,卷积层采样大感受野来得到更多纹理细节;多个DenseRes 叠加模块,级联DenseRes可以让网络更深,效果更好;一个亚像素卷积层作为上采样模块。注意力生成网络部分,用来恢复小的纹理细节,如图像的边缘与形状,网络可以准确定位到细节特征,然后进行相对提升,注意力特征网络设计受到UNet网络架构的启发。完整的模型结构如下:

一个更简介的网络结构如下:

其中LR表示低分辨率图像、HR表示高分辨率图像,Bicubic表示双立方插值上采样。

模型文件

OpenVINO提供的模型是在这个模型基础上进行简化,计算量更低,速度更快。从上面的模型结构知道,模型有两个输入部分,分别是输入的低分辨率图像与双立方上采样的图像

·

·

·

LR的输入:[1x3x270x480]双立方采样:[1x3x1080x1920]三通道顺序是:BGR

模型的输出

·

输出层是一个blob对象,格式为[1x3x1080x1920]

程序演示

首先需要加载网络模型,获取可执行网络,然后设置输入与输出的数据格式与数据精度,这部分的代码如下:

//  加载检测模型

CNNNetReader network_reader;

network_reader.ReadNetwork(model_xml);

network_reader.ReadWeights(model_bin);





// 请求网络输入与输出信息

auto network = network_reader.getNetwork();

InferenceEngine::InputsDataMap input_info(network.getInputsInfo());

InferenceEngine::OutputsDataMap output_info(network.getOutputsInfo());

// 设置输入格式

for (auto &item : input_info) {

      auto input_data = item.second;

      input_data->setPrecision(Precision::U8);

      input_data->setLayout(Layout::NCHW);

      input_data->getPreProcess().setResizeAlgorithm(RESIZE_BILINEAR);

      input_data->getPreProcess().setColorFormat(ColorFormat::BGR);

}

printf("get it \n");





// 设置输出格式

for (auto &item : output_info) {

      auto output_data = item.second;

      output_data->setPrecision(Precision::FP32);

}





// 创建可执行网络对象

auto executable_network = ie.LoadNetwork(network, "CPU");





// 请求推断图

auto infer_request = executable_network.CreateInferRequest();

代码演示步骤中有两个输入,对输入的设置可以使用下面的代码

/** Iterating over all input blobs **/

for (auto & item : input_info) {

      auto input_name = item.first;

      printf("input_name : %s \n", input_name.c_str());

      /** Getting input blob **/

      auto input = infer_request.GetBlob(input_name);

      size_t num_channels = input->getTensorDesc().getDims()[1];

      size_t h = input->getTensorDesc().getDims()[2];

      size_t w = input->getTensorDesc().getDims()[3];

      size_t image_size = h*w;

      Mat blob_image;

      resize(src, blob_image, Size(w, h));

      printf("input channel : %d, height : %d, width : %d \n", num_channels, h, w);

      // NCHW

      unsigned char* data = static_cast<unsigned char*>(input->buffer());

      for (size_t row = 0; row < h; row++) {

              for (size_t col = 0; col < w; col++) {

                       for (size_t ch = 0; ch < num_channels; ch++) {

                                data[image_size*ch + row*w + col] = blob_image.at<Vec3b>(row, col)[ch];

                       }

              }

      }

}

最后执行推理,完成对输出的解析,在解析输出的时候其实输的是[NCHW] = [1x3x1080x1920]的浮点数矩阵,需要转换为Mat类型为[HWC] =[1080x1920x3],采用的是循环方式,是不是有更好的数据处理方法可以转换这个,值得研究。解析部分的代码如下

// 执行预测

infer_request.Infer();





// 处理输出结果

for (auto &item : output_info) {

      auto output_name = item.first;





      // 获取输出数据

      auto output = infer_request.GetBlob(output_name);

      float* buff = static_cast<PrecisionTrait<Precision::FP32>::value_type*>(output->buffer());

      const int c = output->getTensorDesc().getDims()[1];

      const int h = output->getTensorDesc().getDims()[2];

      const int w = output->getTensorDesc().getDims()[3];





      // 获得输出的超像素图像

      Mat result = Mat::zeros(Size(w, h), CV_32FC3);

      for (int ch = 0; ch < c; ch++) {

              for (int row = 0; row < h; row++) {

                       for (int col = 0; col < w; col++) {

                                result.at<Vec3f>(row, col)[ch] = buff[ch*w*h+ row*w + col];

                       }

              }

      }

      printf("channel : %d, height : %d, width : %d \n", c, h, w);

      normalize(result, result, 0, 255.0, NORM_MINMAX);

      result.convertTo(result, CV_8U);

      imshow("High-Resolution Demo", result);

      imwrite("D:/result.png", result);

}

测试结果分别如下:(原图)

超分辨输出:(1920x1080)

总结

也许模型被简化的太厉害了,速度是很快了,单身效果感觉比双立方好那么一点点而已!

本文提出了一种基于注意的方法来区分纹理区域和平滑区域。当高频细节的位置被定位时,注意机制起到了增强高频特征和抑制平滑区域噪声的特征选择器的作用。因此,本文的方法避免了盲目地恢复高频细节。本文将该机制集成到包括SRResNet、VDSR和DRCN的SISR网络中,提高了这些SISR网络的性能。因此,本文验证了注意机制的有效性。对于特征重构网络,本文提出了DenseRes块,它提供了一种将低层特征和高层特征相结合的有效方法。通过多个致密块的级联,本文的网络有一个大的接收场。因此,从LR图像中获取有用的大区域上下文信息,以恢复HR图像中的高频细节。与目前最先进的方法相比,本文的方法具有最好的性能。今后,本文将探索注意机制在视频超分辨率中的应用,以产生直观、定量的高质量结果。

用OpenCV4实现图像的超分别率的更多相关文章

  1. 【opencv系列02】OpenCV4.X图像读取与显示

    一.读取图片 opencv中采用imread() 函数读取图像 imread(filename, flags=None)     filename 图片的路径     flags 图像读取方式 ● c ...

  2. 基于稀疏表示的图像超分辨率《Image Super-Resolution Via Sparse Representation》

    由于最近正在做图像超分辨重建方面的研究,有幸看到了杨建超老师和马毅老师等大牛于2010年发表的一篇关于图像超分辨率的经典论文<ImageSuper-Resolution Via Sparse R ...

  3. JPEG压缩图像超分辨率重建算法

    压缩图像超分辨率重建算法学习 超分辨率重建是由一幅或多幅的低分辨率图像重构高分辨率图像,如由4幅1m分辨率的遥感图像重构分辨率0.25m分辨率图像.在军用/民用上都有非常大应用. 眼下的超分辨率重建方 ...

  4. 【超分辨率】—图像超分辨率(Super-Resolution)技术研究

    一.相关概念 1.分辨率 图像分辨率指图像中存储的信息量,是每英寸图像内有多少个像素点,分辨率的单位为PPI(Pixels Per Inch),通常叫做像素每英寸.一般情况下,图像分辨率越高,图像中包 ...

  5. HMS Core机器学习服务图像超分能力,基于深度学习提升新闻阅读体验

    在移动端阅读资讯时,人们对高分辨率.高质量的图像要求越来越高.但受限于网络流量.存储.图片源等诸多因素,用户无法便捷获得高质量图片.移动端显示设备的高分辨率图片获得问题亟待解决.不久前,HMS Cor ...

  6. paper 89:视频图像去模糊常用处理方法

    随着“平安城市”的广泛建设,各大城市已经建有大量的视频监控系统,虽然监控系统己经广泛地存在于银行.商场.车站和交通路口等公共场所,但是在公安工作中,由于设备或者其他条件的限制,案情发生后的图像回放都存 ...

  7. HTML网页插入图像

    一.WEB上支持的图片格式: GIF:能保存256中颜色,支持透明色,支持动画效果 JPEG:不支持透明色和动画,颜色可达1670种 PNG:支持透明色,不支持动画,颜色有几种到1670种 二.将图片 ...

  8. 【超分辨率】- CVPR2019中SR论文导读与剖析

    CVPR2019超分领域出现多篇更接近于真实世界原理的低分辨率和高分辨率图像对应的新思路.具体来说,以前论文训练数据主要使用的是人为的bicubic下采样得到的,网络倾向于学习bicubic下采样的逆 ...

  9. OpenCV3入门(十四)图像特效—挤压、哈哈镜、扭曲

    一.图像挤压特效 1.原理 图像压效果本质的图像坐标的非线性变换,将图像向内挤压,挤压的过程产生压缩变形,从而形成的效果. 挤压效果的实现是通过极坐标的形式,设图像中心为O(x,y),某点距离中心O的 ...

随机推荐

  1. 【ElasticSearch】shards,replica,index之间的关系

    1.index 包含多个shard ,在创建index的时候可以自定义shards和replica的数量 例如: 新增一个index,手动指定shard和replica的数量 PUT demo_ind ...

  2. hdu4901 枚举状态(找集合对S(xor) ==T(and))

    题意:      给你一个串数字,然后让你在这里面挑取两个集合S ,T,集合的要求是 (1)不能为空 (2)S集合的所有元素必须在T集合的左边 (3)S集合的XOR == T集合的AND      问 ...

  3. 路由协议之RIP

    目录 RIP协议 RIP的路由汇总和过滤 RIP的认证 RIP的防环机制 华为/思科中的配置 RIP协议 RIP协议是一种内部网关协议(IGP),底层是贝尔曼福特算法,是一种动态路由选择协议,用于自治 ...

  4. C++ 三消游戏基本实现

    最近在研究三消算法,我想试试在完全不借助网络资源的情况下搞定这个东西,所以有些地方可能不是最优的. 代码留此备忘. 1. 3x_desk_event.h 1 #pragma once 2 3 #ifn ...

  5. 【Azure Developer】使用Microsoft Graph API 批量创建用户,先后遇见的三个错误及解决办法

    问题描述 在先前的一篇博文中,介绍了如何使用Microsoft Graph API来创建Azure AD用户(博文参考:[Azure Developer]使用Microsoft Graph API 如 ...

  6. Zookeeper详细使用解析!分布式架构中的协调服务框架最佳选型实践

    Zookeeper概念 Zookeeper是分布式协调服务,用于管理大型主机,在分布式环境中协调和管理服务是很复杂的过程,Zookeeper通过简单的架构和API解决了这个问题 Zookeeper实现 ...

  7. 3D教育类小图标_三维立体学习类icon图标素材

    3D教育类小图标_三维立体学习类icon图标素材

  8. PostgreSQL条件表达式

      条件表达式在日常工作中很多场景都会用到,比如某个字段为空,取另外一个字段:某个值大于多少,取什么字段,小于多少取什么字段等等.那么下面来简单的学习下PostgreSQL有那些条件表达式. 1.CA ...

  9. 常用加密算法学习总结之散列函数(hash function)

    散列函数(Hash function)又称散列算法.哈希函数,散列函数把消息或数据压缩成摘要,使得数据量变小,将数据的格式固定下来.该函数将数据打乱混合,重新创建一个叫做散列值(hash values ...

  10. 运维实战案例之“Too many open files”错误与解决方法

    运维实战案例之"Too many open files"错误与解决方法   技术小甜 2017-11-16 15:02:00 浏览869 服务器 shell tomcat 脚本 o ...