1. 图像增广

大规模数据集是成功应用深度神经网络的前提。

  • 图像增广(image augmentation)技术:通过对训练图像做一系列随机改变,来产生相似但又不同的训练样本。

存在以下两点作用:
(1) 扩大训练数据集的规模。
(2) 随机改变训练样本可以降低模型对某些属性的依赖,从而提高模型的泛化能力。
例如,
对图像进行不同方式的裁剪,使感兴趣的物体出现在不同位置,从而减轻模型对物体出现位置的依赖性;
调整亮度、色彩等因素来降低模型对色彩的敏感度。



1.1 函数定义

import numpy as np
import tensorflow as tf
print(tf.__version__)

%matplotlib inline
2.3.0



单张图片读取
import matplotlib.pyplot as plt
img = plt.imread("img/cat1.png")
plt.imshow(img)

输出:

<matplotlib.image.AxesImage at 0x6406f5ba8>



python图像亮度增强的传统方法 python图像增广_数据集


img.shape

输出:

(252, 312, 4)



定义绘图函数show_images
def show_images(imgs, num_rows, num_cols, scale=2):
    figsize = (num_cols*scale, num_rows*scale)
    _, axes = plt.subplots(num_rows, num_cols, figsize=figsize)
    
    for i in range(num_rows):
        for j in range(num_cols):
            axes[i][j].imshow(imgs[i*num_cols+j])

            # 关闭子图中的轴
            axes[i][j].axes.get_xaxis().set_visible(False)
            axes[i][j].axes.get_yaxis().set_visible(False)
            
    return axes



定义辅助函数apply

大部分图像增广方法都有一定的随机性。

为方便观察图像增广的效果,定义辅助函数apply,对输入图像img多次运行图像增广方法aug并展示所有结果:

def apply(img, aug, num_rows=2, num_cols=4, scale=5):
    Y = [aug(img) for _ in range(num_rows*num_cols)]
    show_images(Y, num_rows, num_cols, scale)




1.2 翻转

1.2.1 左右翻转

作为最早且最广泛使用的一种图像增广方法,左右翻转图像通常不改变物体的类别。

通过tf.image.random_flip_left_right实现一半概率的图像左右翻转:

"""
image = np.array([[[1],[2]],[[3],[4]]])
tf.image.random_flip_left_right(image, seed=5).numpy().tolist()
输出:
	[[[1], [2]], [[3], [4]]]
"""

apply(img, tf.image.random_flip_left_right)

输出:



python图像亮度增强的传统方法 python图像增广_数据集_02



1.2.2 上下翻转

上下翻转不如左右翻转通用。

通过tf.image.random_flip_up_down实现一半概率的图像上下翻转:

apply(img, tf.image.random_flip_up_down)

输出:



python图像亮度增强的传统方法 python图像增广_数据集_03




1.3 裁剪

对于上述的样例图像,猫在图像正中间,但一般情况下并非如此。

之前的 池化层 一节中,解释了池化层能降低卷积层对目标位置的敏感度。
除此之外,还可以通过对图像进行随机裁剪,来使物体以不同比例出现在图像的不同位置,从而同样起到降低模型对目标位置敏感性的作用。



假设每次随机裁剪出一块面积为原面积python图像亮度增强的传统方法 python图像增广_python图像亮度增强的传统方法_04的区域,且该区域的宽和高之比随机取自python图像亮度增强的传统方法 python图像增广_池化_05,再将该区域的宽和高分别缩放到200像素。代码实现如下:

aug = tf.image.random_crop
num_rows=2
num_cols=4
scale=5
crop_size=200

Y = [aug(img, (crop_size, crop_size, 3)) for _ in range(num_rows*num_cols)]
show_images(Y, num_rows, num_cols, scale)

输出:



python图像亮度增强的传统方法 python图像增广_池化_06


其中,若无特殊说明,本节中python图像亮度增强的传统方法 python图像增广_代码示例_07python图像亮度增强的传统方法 python图像增广_池化_08之间的随机数,指从区间python图像亮度增强的传统方法 python图像增广_代码示例_09中随机均匀采样所得到的连续值。




1.4 变化颜色

变化颜色也是一种增广方法,可以从4个方面改变图像的颜色,包括:亮度、对比度、饱和度和色调。



1.4.1 改变亮度

将图像的亮度随机变化为原图亮度的python图像亮度增强的传统方法 python图像增广_数据集_10python图像亮度增强的传统方法 python图像增广_代码示例_11,代码示例如下:

aug = tf.image.random_brightness
num_rows=2
num_cols=4
scale=5
max_delta=0.5

Y = [aug(img, max_delta) for _ in range(num_rows*num_cols)]
show_images(Y, num_rows, num_cols, scale)

输出:



python图像亮度增强的传统方法 python图像增广_python图像亮度增强的传统方法_12



1.4.2 改变色调

随机变化图像的色调,代码示例如下:

img_new = img[:,:,:3]

aug = tf.image.random_hue
num_rows=2
num_cols=4
scale=5
max_delta=0.5

Y = [aug(img_new, max_delta) for _ in range(num_rows*num_cols)]
show_images(Y, num_rows, num_cols, scale)

输出:



python图像亮度增强的传统方法 python图像增广_数据集_13




参考

《动手学深度学习》(TF2.0版)