SRGAN生成记录——cv2.resize()以及JPEG保存过程中的信息丢失

首先,JPEG是有损压缩,且这种压缩可迭代,(肉眼看不出差别,但是图像的大小有差别)

import cv2

img1 = cv2.imread('imgresize1.jpeg')
img2 = cv2.resize(img1,(256,256))
cv2.imwrite("imgresize2.jpeg",img2)

如果我用这种方式保存图像的话,默认的压缩参数是95,

原图是1460KB,一次压缩变成46KB,再次变成15KB,即使后两者的图像分辨率都是256*256

SRGAN生成记录——cv2.resize()以及JPEG保存过程中的信息丢失_第1张图片

正确的操作是把最后一句变成:

cv2.imwrite("imgresize3.jpeg",img2,[int(cv2.IMWRITE_JPEG_QUALITY), 100])

------------------------------------------------------------------------

其次,JPEG的压缩方式,是将图像分成许多个8*8的小block,对每一个block做DCT离散余弦变换,丢失大量高频信息。

(低频部分集中在每个8*8块的左上角,高频部分在右下角,所谓JPEG的有损压缩,损的是量化过程中的高频部分)

因此,在SRGAN 生成的过程中,观察到许多细小的artifact,如下图:

SRGAN生成记录——cv2.resize()以及JPEG保存过程中的信息丢失_第2张图片

去除这种artifact的方式可以参考ARCNN(Deep Convolution Networks for Compression Artifacts Reduction, ICCV2015)

建议是要将artifact removal和super resolution分开做。

--------------------------------------------------------------------------------

最后,本着打破砂锅问到底的探究精神,cv2.resize()函数到底对图像做了什么?

参考了网上的很多教程,都是在讲如何使用,或者如果把图片放大怎么插值,但是我想知道的是,如果原图为256*256,resize成128*128,信息是如何损失的?

于是我去查了源码,https://github.com/opencv/opencv/blob/master/modules/imgproc/src/resize.cpp

3000多行,菜鸡如我当然看不懂...机缘巧合看到知乎手撕源码的大佬https://zhuanlan.zhihu.com/p/36736315

直接说结论:就是把几个点加权平均。

看最简单的情况下(例如把256*256resize成128*128):

   if (cn == 1)
            for( ; dx < w; ++dx )
            {
                int index = dx*2;
                D[dx] = (T)((S[index] + S[index+1] + nextS[index] + nextS[index+1] + 2) >> 2);
            }

做了个小测试,原图为46KB,缩小以后为14KB,约为1/4的关系(不知道这样理解对不对..)

 

其他参考链接:

https://blog.csdn.net/u013752202/article/details/78551592

https://www.zhihu.com/question/65058389

你可能感兴趣的:(keras,python)