首页 > 其他分享 >【图像超分】论文复现:新手入门!Pytorch实现SRCNN,数据预处理、模型训练、测试、评估全流程详解,注释详细,简单修改就可以训练你自己的图像数据,有训练好的模型下载地址,随取随用

【图像超分】论文复现:新手入门!Pytorch实现SRCNN,数据预处理、模型训练、测试、评估全流程详解,注释详细,简单修改就可以训练你自己的图像数据,有训练好的模型下载地址,随取随用

时间:2024-03-13 11:02:01浏览次数:17  
标签:img 训练 self SSIM window 图像 模型 size

文章目录


前言

论文地址:Image Super-Resolution Using Deep Convolutional Networks

论文精读:【图像超分】论文精读:Image Super-Resolution Using Deep Convolutional Networks(SRCNN)

请配合上述论文精读文章使用,效果更佳!

代码地址:图像超分辨率SRCNN和FSRCNN复现代码,除基本的网络实现外,还有特征图可视化,PSNR曲线图可视化,测试自己的图像数据等

不想理解原理,希望直接跑通然后应用到自己的图像数据的同学,请直接下载上面的代码,有训练好的模型,直接用即可。具体使用方式见代码中的README!有问题来本文评论区留言!

深度学习的模型训练一般遵循以下步骤:

  1. 准备数据集,以及数据预处理
  2. 搭建网络模型
  3. 设置参数并训练
  4. 测试训练好的模型
  5. 用训练好的模型测试自己的数据

下面让我们根据通用流程,一步一步复现SRCNN吧!目标是:输入大小为 h×w 的图像 X,输出为一个 sh×sw 的图像 Y,s 为放大倍数。论文中s取值为2,3,4。

注:放大倍数为1,则图像分辨率不变,只是图像变清晰!如果你只是想将模糊图像通过SRCNN超分后变清晰,那么请将该参数设置为1。

硬件环境:windows11+RTX 2060(比这个高肯定没问题,我这个配置本机跑500个epoch一点问题没有,一会就跑完。但超分自己的图像时,如果图像很大,可能有内存溢出的错误
运行环境:jupyter notebook/pycharm(前者好处是分代码段运行,测试方法,适合学习用;后者适合跑完整项目用
pytorch环境:torch1.9.1+cuda11.1(其他版本没测试过,应该问题不大)

1. 准备数据集和数据预处理

1.1 数据集选择

简单回顾论文中出现过的数据集:

  • 训练集(Train dataset):91 images、ILSVRC 2013 ImageNet
  • 测试集(Test dataset):Set5、Set14、BSD200

由于91 images的数据处理有些繁琐,对于新手不太友好,而ImageNet数据集过大,可能不利于硬件设备不好的同学,所以本文使用折中的BSD200数据集,包含200张图像训练集和200张图像测试集

1.2 数据预处理

根据论文中第4节实验部分开头所述,RGB 颜色模式色调、色度、饱和度三者混在一起难以分开,超分只用于YCbCr的Y通道,即亮度分量。因此,需要将图像数据由RGB模型转换成 YCbCr 颜色模式,Y 是指亮度分量,Cb 表示 RGB 输入信号蓝色部分与 RGB 信号亮度值之间的差异,Cr 表示 RGB 输入信号红色部分与 RGB 信号亮度值之间的差异。

此外,通过观察BSD200数据集中的图像可知,数据集中的图像宽高并不一致,每张图像的大小也千差万别。而SRCNN要求输入图像的长宽一致,所以在训练之前,需要将图像裁剪成宽高一致的图像。采用的策略是按图像中心外扩,resize成300×300的图像。

数据预处理的代码如下:

# 判断某个文件是否是图像
# enswith判断是否以指定的.png,.jpg,.jpeg结尾的字符串
# 可以根据情况扩充图像类型,加入.bmp、.tif等
def is_image_file(filename):
    return any(filename.endswith(extension) for extension in [".png", ".jpg", ".jpeg"])

# 读取图像转为YCbCr模式,得到Y通道
def load_img(filepath):
    img = Image.open(filepath).convert('YCbCr')
    y, _, _ = img.split()
    return y

# 裁剪大小,宽高一致为300
# 如果想训练自己的数据集,请根据情况修改裁剪大小
CROP_SIZE = 300

# 封装数据集,适配后面的torch.utils.data.DataLoader中的dataset,定义成类似形式
# 类参数为图像文件夹路径和放大倍数
# __len__(self) 定义当被len()函数调用时的行为(返回容器中元素的个数)
#__getitem__(self) 定义获取容器中指定元素的行为,相当于self[key],即允许类对象可以有索引操作。
#__iter__(self) 定义当迭代容器中的元素的行为
# 返回输入图像和标签,传入DataLoader的dataset参数
class DatasetFromFolder(Dataset):
    def __init__(self, image_dir, zoom_factor):
        super(DatasetFromFolder, self).__init__()
        self.image_filenames = [join(image_dir, x) for x in listdir(image_dir) if is_image_file(x)] # 图像路径列表
        crop_size = CROP_SIZE - (CROP_SIZE % zoom_factor) # 处理放大倍数,防止用户瞎设置,本例只能设置为2,3,4,大小不变
        # 数据集变换
        # 还有一些其他的变换操作,如归一化等,遇到一个积累一个
        self.input_transform = transforms.Compose([transforms.CenterCrop(crop_size), # 从图片中心裁剪成300*300
                                                   transforms.Resize(
                                                       crop_size // zoom_factor),    # Resize, 输入应该是缩放倍数后的图像,因为先缩小后放大
                                                   transforms.Resize(
                                                       crop_size, interpolation=Image.BICUBIC), # 双三次插值
                                                   transforms.ToTensor()]) # 图像转成tensor
        # label标签,超分不是分类问题,定义成一样的就行
        self.target_transform = transforms.Compose(
            [transforms.CenterCrop(crop_size), transforms.ToTensor()])

    def __getitem__(self, index):
        input = load_img(self.image_filenames[index]) # 输入是图像的Y通道,即亮度通道
        target = input.copy()
        input = self.input_transform(input)
        target = self.target_transform(target)
        return input, target

    def __len__(self):
        return len(self.image_filenames) # 图像个数

至此,数据预处理完成,训练之前就可以传入DataLoader的dataset参数中。

1.3 评估指标PSNR和SSIM

训练过程中,每个epoch会得到一个SRCNN的模型。那么如何评价该模型的性能呢?需要两个评价指标:PSNR和SSIM。由于训练时需要用到,所以需要提前将计算PSNR和SSIM的代码准备好。

1.3.1 PSNR

PSNR(Peak Signal to Noise Ratio)为峰值信噪比,计算公式如下:
M S E = 1 H × W ∑ i = 1 H ∑ j = 1 W ( X ( i , j ) − Y ( i , j ) ) 2 M S E=\frac{1}{H \times W} \sum_{i=1}^{H} \sum_{j=1}^{W}(X(i, j)-Y(i, j))^{2} MSE=H×W1​i=1∑H​j=1∑W​(X(i,j)−Y(i,j))2
P S N R = 10 log ⁡ 10 ( ( 2 n − 1 ) 2 M S E ) P S N R=10 \log _{10}\left(\frac{\left(2^{n}-1\right)^{2}}{M S E}\right) PSNR=10log10​(MSE(2n−1)2​)
其中,MSE是均方误差。两个图像对应像素位置的值相减再平方和最后取平均。n是每像素的比特数,一般取256。PSNR的单位是dB,该值越大表示图像的失真越小。

通常认为,PSNR在38以上的时候,人眼就无法区分两幅图片了。

PSNR的计算代码如下:

def psnr(loss):
    return 10 * log10(1 / loss.item())

损失函数使用的就是MSE,所以这么定义。log10是python的math库中的包。

做实验的时候,PSNR一般保留两位小数。

1.3.2 SSIM

SSIM(Structural Similarity,结构相似性)由三个对比模块组成:亮度、对比度、结构。
在这里插入图片描述
(1) 亮度对比函数
图像平均灰度:
μ X = 1 H × M ∑ i = 1 H ∑ j = 1 M X ( i , j ) \mu_{X}=\frac{1}{H \times M} \sum_{i=1}^{H} \sum_{j=1}^{M} X(i, j) μX​=H×M1​i=1∑H​j=1∑M​X(i,j)
亮度对比函数:
l ( x , y ) = 2 μ x μ y + C 1 μ x 2 + μ y 2 + C 1 l(x, y)=\frac{2 \mu_{x} \mu_{y}+C_{1}}{\mu_{x}^{2}+\mu_{y}^{2}+C_{1}} l(x,y)=μx2​+μy2​+C1​2μx​μy​+C1​​

(2) 对比度对比函数
图像的标准差:
σ X = ( 1 H + W − 1 ∑ i = 1 H ∑ j = 1 M ( X ( i , j ) − μ X ) 2 ) 1 2 \sigma_{X}=\left(\frac{1}{H+W-1} \sum_{i=1}^{H} \sum_{j=1}^{M}\left(X(i, j)-\mu_{X}\right)^{2}\right)^{\frac{1}{2}} σX​=(H+W−11​i=1∑H​j=1∑M​(X(i,j)−μX​)2)21​
对比度对比函数:
c ( x , y ) = 2 σ x σ y + C 2 σ x 2 + σ y 2 + C 2 c(x, y)=\frac{2 \sigma_{x} \sigma_{y}+C_{2}}{\sigma_{x}^{2}+\sigma_{y}^{2}+C_{2}} c(x,y)=σx2​+σy2​+C2​2σx​σy​+C2​​

(3) 结构对比函数
s ( x , y ) = σ x y + C 3 σ x σ y + C 3 s(x, y)=\frac{\sigma_{x y}+C_{3}}{\sigma_{x} \sigma_{y}+C_{3}} s(x,y)=σx​σy​+C3​σxy​+C3​​

综合上述三个部分,得到 SSIM 计算公式:

SSIM ⁡ ( x , y ) = f ( l ( x , y ) , c ( x , y ) , s ( x , y ) ) = [ l ( x , y ) ] α [ c ( x , y ) ] β [ s ( x , y ) ] γ \begin{aligned} \operatorname{SSIM}(x, y) & =f(l(x, y), c(x, y), s(x, y)) \\ & =[l(x, y)]^{\alpha}[c(x, y)]^{\beta}[s(x, y)]^{\gamma} \end{aligned} SSIM(x,y)​=f(l(x,y),c(x,y),s(x,y))=[l(x,y)]α[c(x,y)]β[s(x,y)]γ​

其中,

标签:img,训练,self,SSIM,window,图像,模型,size
From: https://blog.csdn.net/qq_36584673/article/details/136452618

相关文章

  • 使用 Keras 和 ArcGIS Pro 通过 Mask-RCNN/DeepLabV3+ 进行 EagleView 高分辨率图像语
            机器学习中的计算机视觉为GIS提供了巨大的机会。其任务包括获取、处理、分析和理解数字图像的方法,以及从现实世界中提取高维数据以产生数字或符号信息,例如以决策的形式。在过去的几年中,计算机视觉越来越多地从传统的统计方法转向最先进的深度学习神经网络技......
  • 【算法训练营】最长公共子序列,倒水问题,奶牛吃草(Python实现)
    最长公共子序列时间限制:1sec空间限制:256MB问题描述给定两个1到n的排列A,B(即长度为n的序列,其中[1,n]之间的所有数都出现了恰好一次)。求它们的最长公共子序列长度。输入格式第一行一个整数n,意义见题目描述。第二行n个用空格隔开的正整数A[1],…,......
  • 【算法训练营】邓老师书,子序列,前缀(python实现)
    邓老师数时间限制:1sec空间限制:256MB问题描述众所周知,大于1的自然数中,除了1与其本身外不再有其他因数的数称作质数(素数)。对于大于1的不是质数的自然数,我们又称作合数。参加了邓老师算法训练营的小Z突发奇想,定义了新的数:所有合数中,除了1与其本身外,其他因......
  • 3D模型+BI分析,打造全新的交互式3D可视化大屏开发方案
    背景介绍在数字经济建设和数字化转型的浪潮中,数据可视化大屏已成为各行各业的必备工具。然而,传统的数据大屏往往以图表和指标为主,无法真实地反映复杂的物理世界和数据关系。为了解决这个问题,3D模型可视化和数字孪生技术应运而生,它们可以将真实世界的物理对象、过程或系统,以及它们......
  • 使用libtorch训练一个异或逻辑门
    本文以一个例子介绍如何使用libtorch创建一个包含多层神经元的感知机,训练识别异或逻辑。即${z= x\text{^}y}$。本例的测试环境是VS2017和libtorch1.13.1。从本例可以学到如何复用网络结构,如下方的LinearSigImpl类的写法。该测试网络结构如下图。一个线性层2输入3输出,一个Sig......
  • 视觉slam十四讲CH5 ---相机与图像
    视觉slam十四讲---CH5相机与图像视觉slam中,作为主要传感器的相机自然起到着重要的作用,而相机拍摄的图像及其处理也是我们要做的工作之一。1.相机模型单目相机的针孔模型上图中的模型即为常见的单目相机的针孔模型示意。从5-1的左边我们可以看到有很多坐标系交杂在一......
  • 【网络基础学习之一】OSI参考模型与TCP/IP协议
    一.分层思想1.分层背景OSI(OpenSystemsInterconnection,开放式系统互联)是国际标准化组织(ISO)在20世纪80年代制定的一种通信协议的通信模型,主要用于计算机网络中,规定了计算机系统之间通信的标准方法和协议。2.分层优点各层之间相互独立,每一层只实现一种相对独立的功能,使问题复......
  • 监控大模型训练
    监控大模型训练大模型训练时间久,而且过程中容易出现各种各样的问题而中断,中断之后不及时续练的话对GPU资源是很大的浪费,但是我们又不能一直盯着程序。所以本文将介绍如何编写一个监控程序来监控大模型的训练,以方便我们在大模型训练出现异常时及时通知给我们。监控的方式有很多,这......
  • 自然语言处理(NLP)—— 生成式模型和判别式模型
            生成式模型和判别式模型是机器学习领域两大类模型,它们在自然语言处理、计算机视觉等领域都有广泛的应用。理解这两类模型的区别对于选择正确的模型来解决特定问题非常重要。1.生成式模型(GenerativeModels)        生成式模型旨在学习数据的联合......
  • envi5.6对多个图像的同地点数据对比
    一:多视图窗口创建点击Views中的CreateNewView这里创建了两个窗口,也可以再次进行上述操作,创造第三个视图  二:图像的输入选择要对比的文件分别拖动到两个视窗(这里以①和②为例)中 三:链接图像对比点击如图红圈标记的按钮 把如图标记的按钮都打开接下来便可以在......