Keras神经网络的学习与使用(4)-数据增强

5 篇文章 2 订阅
3 篇文章 0 订阅

数据增强的作用

深度学习有3个核心要素,分别是:

  • 优秀的算法设计
  • 高性能的计算能力
  • 大数据

因此在我们拥有优秀的算法设计和高性能的计算能力的同时,我们也需要大量的高质量数据。
但是,对于个人,学校团队甚至普通的工程师团队来说,数据的搜集能力都是十分有限的。缺乏大量高质量的训练样本,便难以训练处一个具有很好泛化能力的模型。因此,我们就需要一些数据集扩充的方法,即我们常说的数据增强

数据增强的概述

对于图像处理的场景,数据增强自然是对图片而言。数据增强就是指对图片数据进行变换、修改,使其变成新的图片数据,从而扩充我们的图片数据集。
图片数据增强的方法主要包括以下几个:

  • 随机裁剪
  • 颜色改变
  • 水平或竖直翻转
  • 随机改变大小
  • 加入噪声
  • 对图片进行仿射变换

通过使用数据增强的方法来实现数据集的扩充,可以使训练后的模型具有更好的鲁棒性,尤其是对噪声的抵抗能力得到强化,进而提高训练后模型的泛化能力
鲁棒性:

1.模型具有较高的精度或有效性,这也是对于机器学习中所有学习模型的基本要求;
2.对于模型假设出现的较小偏差,只能对算法性能产生较小的影响; 主要是:噪声(noise)
3.对于模型假设出现的较大偏差,不可对算法性能产生“灾难性”的影响;主要是:离群点(outlier)

泛化能力

在机器学习方法中,泛化能力通俗来讲就是指学习到的模型对未知数据的预测能力。在实际情况中,我们通常通过测试误差来评价学习方法的泛化能力。如果在不考虑数据量不足的情况下出现模型的泛化能力差,那么其原因基本为对损失函数的优化没有达到全局最优。

Keras实现数据增强

Keras为我们提供的数据增强功能是通过ImageDataGenerator类来实现的。ImageDataGenerator类主要通过生成器(generator)的方式来产生经过变化的新图片。生成器是Python提供的一个高级特性,对于list这样的容器,其中的元素是预先存储在内存中的。而生成器的特点是其中的一个元素一边生成,一边使用。换句话说,当我们遍历list时,遍历的是已经存在于list中的元素,而生成器中的元素是在遍历的过程中同时生成的,这是一种流式的效果。

keras.preprocessing.image.ImageDataGenerator(
                 featurewise_center=False,
                 samplewise_center=False,
                 featurewise_std_normalization=False,
                 samplewise_std_normalization=False,
                 zca_whitening=False,
                 zca_epsilon=1e-6,
                 rotation_range=0,
                 width_shift_range=0.,
                 height_shift_range=0.,
                 brightness_range=None,
                 shear_range=0.,
                 zoom_range=0.,
                 channel_shift_range=0.,
                 fill_mode='nearest',
                 cval=0.,
                 horizontal_flip=False,
                 vertical_flip=False,
                 rescale=None,
                 preprocessing_function=None,
                 data_format='channels_last',
                 validation_split=0.0,
                 interpolation_order=1,
                 dtype='float32')
  • featurewise_center:布尔值,是否将输入数据的均值设置为0。
  • samplewise_center:布尔值,是否将每个样本的均值设置为0。
  • featurewise_std_normalization:布尔值,是否将输入特征除以其标准值。
  • samlewise_std_normalization:布尔值,是否将每个输入样本除以其标准差。
  • zca_epsilon:ZCA白化的ε值,默认为1e-6。
  • zca_whitening:布尔值,决定是否应用ZCA白化的方式进行数据增强。
  • rotation_range:整数值,决定随机旋转的度数。
  • width_shift_range:浮点数、整数或者其数组,水平位置平移值。
  • height_shift_range:浮点数、整数或者其数组,垂直位置平移值。
  • shear_range:浮点数,图片剪切的强度。
  • zoom_range:浮点数或者一个区间,表示随机缩放的范围,形如[0.1, 0.2],分别表示其上界和下界。
  • channel_shift_range:浮点数,随机通道偏移的幅度。
  • fill_mode:“constant” “nearest” “reflect”或“wrap”之一,默认为“nearest”。当进行变换时,超出边界的点将根据本参数给定的方法进行处理。假设填充序列“abcd”两侧的数值,其中每个参数的填充方式如下。
  1. constant:kkkkkkkk|abcd|kkkkkkkk(假设cval参数值为k时)
  2. nearest:aaaaaaaa|abcd|dddddddd
  3. reflect:abcddcba|abcd|dcbaabcd
  4. wrap:abcdabcd|abcd|abcdabcd
  • cavl:浮点数或整型,详见fill_mode参数;
  • horizontal_flip:布尔值,是否随机水平翻转;
  • vertical_flip:布尔值,是否随机垂直翻转;
  • rescale:重缩放因子的数值,将数据乘以所提供的参数值。如果不指定该参数则默认为None。如果是None或0,则不进行缩放;
  • preprocessing_function:指定一个回调函数,这个函数会在其它任何操作之前运行。这个函数需要一个参数——图片数据(秩为3的Numpy张量)
  • data_format:图像数据格式。
  • validation_split:是一个在[0, 1]区间的浮点数,表示保留用于验证的图像比例。
keras.preprocessing.image.ImageDataGenerator.flow( x,
	  y=None,
	   batch_size=32,
	   shuffle=True,
	   sample_weight=None,
	   seed=None,
	   save_to_dir=None,
	   save_prefix='',
	   save_format='png',
	   subset=None):

接收numpy数组和标签为参数,生成经过数据提升或标准化后的batch数据,并在一个无限循环中不断的返回batch数据

  • x:样本数据,秩应为4.在黑白图像的情况下channel轴的值为1,在彩色图像情况下值为3

  • y:标签

  • batch_size:整数,默认32

  • shuffle:布尔值,是否随机打乱数据,默认为True

  • save_to_dir:None或字符串,该参数能让你将提升后的图片保存起来,用以可视化

  • save_prefix:字符串,保存提升后图片时使用的前缀, 仅当设置了save_to_dir时生效

  • save_format:“png"或"jpeg"之一,指定保存图片的数据格式,默认"jpeg”

  • yields:形如(x,y)的tuple,x是代表图像数据的numpy数组.y是代表标签的numpy数组.该迭代器无限循环.

  • seed: 整数,随机数种子

使用示例:
注:本示例是在pycharm下运行,在flow()方法中需要设置正确的路径。

import numpy as np
from keras.preprocessing.image import ImageDataGenerator, img_to_array, load_img

datagen = ImageDataGenerator(
    rotation_range=40, width_shift_range=0.2, height_shift_range=0.2, rescale=1 / 255,
    shear_range=20, zoom_range=0.2, horizontal_flip=True, fill_mode='nearest')

img = load_img('demo.jpg')
x = img_to_array(img)
# 扩展数组的形状
x = np.expand_dims(x, 0)

# 生成20张图片
i = 0
for batch in datagen.flow(x, batch_size=1, save_to_dir='genreate_images',
                          save_prefix='new',
                          save_format='jpg'):
    i += 1
    if i == 20:
        break
print('image generate finished!')

图片文件夹

数据增强

自己实现数据增强

import cv2
import numpy as np
import scipy.ndimage as ndi


def do_random_crop_and_rotation(image_array, translation_factor, zoom_range):
    height = image_array.shape[0]
    width = image_array.shape[1]

    x_offset = np.random.uniform(0, translation_factor * width)
    y_offset = np.random.uniform(0, translation_factor * height)

    offset = np.array([x_offset, y_offset])

    scale_factor = np.random.uniform(zoom_range[0], zoom_range[1])
    crop_matrix = np.array([[scale_factor, 0], [0, scale_factor]])

    image_array = np.rollaxis(image_array, axis=-1, start=0)
    # ndi.interpolation 插值
    image_channel =[ndi.interpolation.affine_transform(image_channel, crop_matrix, offset=offset,
                                                        order=0, mode='nearest',
                                                        cval=0.0) for image_channel in image_array]

    image_array = np.stack(image_channel, axis=0)
    image_array = np.rollaxis(image_array, 0, 3)
    return image_array


if __name__ == '__main__':
   raw_img = cv2.imread('demo.jpg')
   cropped_and_rotated_img = do_random_crop_and_rotation(raw_img, 0.3, [0.75, 1.25])
   cv2.imwrite('new_demo.jpg', cropped_and_rotated_img)

数据增强

该函数实现的事仿射变换,利用仿射变换对图片进行旋转与裁剪。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值