keras的数据增强,有篇博客写的不错博客地址
keras关于数据增强的介绍keras数据增强
from keras.preprocessing.image import ImageDataGenerator, array_to_img, img_to_array, load_img
datagen = ImageDataGenerator(featurewise_center=True,featurewise_std_normalization=True,rotation_range=20,width_shift_range=0.2,height_shift_range=0.2,horizontal_flip=True)
img = load_img('cat.jpeg') # 这是一个PIL图像
x = img_to_array(img) # 把PIL图像转换成一个numpy数组,形状为(3, 150, 150)
x = x.reshape((1,) + x.shape) # 这是一个numpy数组,形状为 (1, 3, 150, 150)
#计算依赖于数据的变换所需要的统计信息(均值方差等),只有使用featurewise_center,featurewise_std_normalization或zca_whitening时需要此函数。
#datagen.fit(x)
# 下面是生产图片的代码
# 生产的所有图片保存在 `data1/` 目录下
i = 0
for batch in datagen.flow(x, batch_size=1,save_to_dir='data1', save_prefix='cat', save_format='jpeg'):
i += 1
if i > 50:
break # 否则生成器会退出循环
当没有加datagen.fit()这个函数时,会报这个警告:
当加上datagen.fit()这句话时(即把上面代码中#datagen.fit()的#符号去掉),就不会报上面的警告
结果:
keras实现mnist:
import os
import numpy as np
import tensorflow
from keras.models import *
from keras.layers import Input, merge, Conv2D, MaxPooling2D, UpSampling2D, Dropout, Cropping2D,Dense,Reshape
from keras.optimizers import *
from keras.callbacks import ModelCheckpoint, LearningRateScheduler
from keras import backend as keras
import keras
from keras.preprocessing.image import ImageDataGenerator
from keras.datasets import mnist
import scipy.io as sio
class myUnet(object):
def get_unet(self):
inputs = Input((self.img_rows, self.img_cols,1))
conv1 =Conv2D(32, 3, activation='relu', padding='same', kernel_initializer='he_normal')(inputs)
conv2 = Conv2D(64, 3, activation='relu', padding='same', kernel_initializer='he_normal')(conv1)
conv3=MaxPooling2D(pool_size=(2, 2))(conv2)
conv4=keras.layers.core.Dropout(0.25, noise_shape=None, seed=None)(conv3)
conv5=keras.layers.core.Flatten()(conv4)
conv6 = Dense(128)(conv5)
conv7 = keras.layers.core.Dropout(0.5, noise_shape=None, seed=None)(conv6)
conv8=Dense(10, activation='softmax')(conv7)
model = Model(input = inputs, output = conv8)
model.compile(optimizer=Adam(lr=1e-4), loss='categorical_crossentropy', metrics=['accuracy'])
return model
def train(self):
print("loading data")
(x_train, y_train), (x_test, y_test) = mnist.load_data()
img_rows=28;
img_cols=28
num_classes=10
if K.image_data_format() == 'channels_first':
x_train = x_train.reshape(x_train.shape[0], 1, img_rows, img_cols)
x_test = x_test.reshape(x_test.shape[0], 1, img_rows, img_cols)
# 单通道灰度图像,channel=1
input_shape = (1, img_rows, img_cols)
else:
x_train = x_train.reshape(x_train.shape[0], img_rows, img_cols, 1)
x_test = x_test.reshape(x_test.shape[0], img_rows, img_cols, 1)
input_shape = (img_rows, img_cols, 1)
# 数据转为float32型
x_train = x_train.astype('float32')
x_test = x_test.astype('float32')
print('y_test:', x_train.shape)
print('y_test:', y_test.shape)
# 先通过np生成一个1000*1维的其值为0-9的矩阵,然后再通过```keras.utils.to_categorical```方法获取成一个1000*10维的二元矩阵。比如当那一行的数为5时生成的新的一行为[0,0,0,0,0,1,0,0,0,0]即第6个数为1,其它为0
y_train = keras.utils.to_categorical(y_train, num_classes)
y_test = keras.utils.to_categorical(y_test, num_classes)
print('y_test:',y_test.shape)
print("loading data done")
#datagen = ImageDataGenerator(featurewise_center=True, featurewise_std_normalization=True, rotation_range=20,width_shift_range=0.2, height_shift_range=0.2, horizontal_flip=True)
model = self.get_unet()
model_checkpoint = ModelCheckpoint('unet.hdf5', monitor='loss',verbose=1, save_best_only=True)
print('Fitting model...')
#model.fit_generator(datagen.flow(x_train, y_train, batch_size=12),steps_per_epoch=x_train.shape[0], epochs=10, verbose=1)
model.fit(x_train, y_train, batch_size=100, nb_epoch=10, verbose=1,validation_split=0.1, shuffle=True, callbacks=[model_checkpoint])
score = model.evaluate(x_test, y_test, verbose=0)
print('Test loss:', score[0])
print('Test accuracy:', score[1])
model.save('a_rcnn1.h5')
if __name__ == '__main__':
myunet = myUnet()
myunet.train()
其中(x_train, y_train), (x_test, y_test) = mnist.load_data()的数据会下载到下面路径
- path:如果你在本机上已有此数据集(位于
'~/.keras/datasets/'+path
),则载入。否则数据将下载到该目录下 - 关于keras的mnist数据集合的介绍
其中.keras下还有个文件:keras.json 内容:
{
"floatx": "float32",
"epsilon": 1e-07,
"image_data_format": "channels_last",
"backend": "tensorflow"
}
如果将tensorflow改为theano那么backend就会变为theano
我的训练结果为:
keras采用数据增强:
import os
import numpy as np
import tensorflow
from keras.models import *
from keras.layers import Input, merge, Conv2D, MaxPooling2D, UpSampling2D, Dropout, Cropping2D,Dense,Reshape
from keras.optimizers import *
from keras.callbacks import ModelCheckpoint, LearningRateScheduler
from keras import backend as keras
import keras
from keras.preprocessing.image import ImageDataGenerator
from keras.datasets import mnist
import scipy.io as sio
class myUnet(object):
def get_unet(self):
inputs = Input((self.img_rows, self.img_cols,1))
conv1 =Conv2D(32, 3, activation='relu', padding='same', kernel_initializer='he_normal')(inputs)
conv2 = Conv2D(64, 3, activation='relu', padding='same', kernel_initializer='he_normal')(conv1)
conv3=MaxPooling2D(pool_size=(2, 2))(conv2)
conv4=keras.layers.core.Dropout(0.25, noise_shape=None, seed=None)(conv3)
conv5=keras.layers.core.Flatten()(conv4)
conv6 = Dense(128)(conv5)
conv7 = keras.layers.core.Dropout(0.5, noise_shape=None, seed=None)(conv6)
conv8=Dense(10, activation='softmax')(conv7)
model = Model(input = inputs, output = conv8)
model.compile(optimizer=Adam(lr=1e-4), loss='categorical_crossentropy', metrics=['accuracy'])
return model
def train(self):
print("loading data")
(x_train, y_train), (x_test, y_test) = mnist.load_data()
img_rows=28;
img_cols=28
num_classes=10
if K.image_data_format() == 'channels_first':
x_train = x_train.reshape(x_train.shape[0], 1, img_rows, img_cols)
x_test = x_test.reshape(x_test.shape[0], 1, img_rows, img_cols)
# 单通道灰度图像,channel=1
input_shape = (1, img_rows, img_cols)
else:
x_train = x_train.reshape(x_train.shape[0], img_rows, img_cols, 1)
x_test = x_test.reshape(x_test.shape[0], img_rows, img_cols, 1)
input_shape = (img_rows, img_cols, 1)
# 数据转为float32型
x_train = x_train.astype('float32')
x_test = x_test.astype('float32')
print('y_test:', x_train.shape)
print('y_test:', y_test.shape)
# 先通过np生成一个1000*1维的其值为0-9的矩阵,然后再通过```keras.utils.to_categorical```方法获取成一个1000*10维的二元矩阵。比如当那一行的数为5时生成的新的一行为[0,0,0,0,0,1,0,0,0,0]即第5个数为1,其它为0
y_train = keras.utils.to_categorical(y_train, num_classes)
y_test = keras.utils.to_categorical(y_test, num_classes)
print('y_test:',y_test.shape)
print("loading data done")
#具体说明看官方文档
datagen = ImageDataGenerator(featurewise_center=True, featurewise_std_normalization=True, rotation_range=20,width_shift_range=0.2, height_shift_range=0.2, horizontal_flip=True)
model = self.get_unet()
model_checkpoint = ModelCheckpoint('unet.hdf5', monitor='loss',verbose=1, save_best_only=True)
print('Fitting model...')
#batch_size就是一张图片要生成多少张图片,这里为12,steps_per_epoch就是一次epochs要取多少张图片,这里是训练图片的个数
model.fit_generator(datagen.flow(x_train, y_train, batch_size=12),steps_per_epoch=x_train.shape[0], epochs=10, verbose=1)
#model.fit(x_train, y_train, batch_size=100, nb_epoch=10, verbose=1,validation_split=0.1, shuffle=True, callbacks=[model_checkpoint])
score = model.evaluate(x_test, y_test, verbose=0)
print('Test loss:', score[0])
print('Test accuracy:', score[1])
model.save('a_rcnn1.h5')
if __name__ == '__main__':
myunet = myUnet()
myunet.train()
结果好像很差,这里就不贴出来了,可能是因为数据增强 用了
featurewise_center
,
featurewise_std_normalization
或
zca_whitening
操作导致数据不好,具体原因,有待参考。