概要
この記事の一部です。
目標:顔が写っている画像から、男女を識別したい。
全体の流れ
- 男女別のラベルが付いている画像データを用意。
- VGG16を転移学習させる
1. 男女別のラベルが付いている画像データを用意。
UTKFaceのデータセットを利用。
もともと顔の部分のみ切り取られた画像のものと、上半身が写っている画像のものが用意されているが、実際に適用したい画像はdlibでマージンをつけて切り取ったものなので、こちらも同様にdlibで切り取った。
#2. VGG16を転移学習させる
vgg_face.py
import os
import glob
import numpy as np
import keras
import matplotlib.pyplot as plt
%matplotlib inline
img_width, img_height = 224, 224
from keras.preprocessing.image import ImageDataGenerator
# data augumentation
train_datagen = ImageDataGenerator(
rescale=1.0 / 255,
zca_whitening=True,
rotation_range=20,
zoom_range=0.2,
width_shift_range=0.2,
height_shift_range=0.2,
horizontal_flip=True
)
test_datagen = ImageDataGenerator(rescale=1.0 / 255)
from keras.models import Sequential, Model
from keras.layers import Dense, Input, Flatten, Dropout
from keras.applications.vgg16 import VGG16
# set input layer and load vgg16
input_tensor = Input(shape=(img_height, img_width, 3))
vgg16_model = VGG16(include_top=False, input_tensor=input_tensor)
# 14層目までのモデル重みを固定(VGG16のモデル重みを用いる)
for layer in vgg16_model.layers[:15]:
layer.trainable = False
# define FC layer
fc_model = Sequential()
fc_model.add(Flatten(input_shape=vgg16_model.output_shape[1:]))
fc_model.add(Dense(256, activation='relu'))
fc_model.add(Dropout(0.5))
fc_model.add(Dense(1, activation='sigmoid'))
model = Model(inputs=vgg16_model.input, outputs=fc_model(vgg16_model.output))
model.compile(
# optimizer = "adam", これはうまく行かないらしい
optimizer=keras.optimizers.SGD(lr=1e-4, momentum=0.9),
loss='binary_crossentropy',
metrics=['accuracy']
)
# es_cb = keras.callbacks.EarlyStopping(monitor='val_loss', patience=0, verbose=0, mode='auto')
tb_cb = keras.callbacks.TensorBoard(log_dir="./logs")
#VGG
train_data_dir = './margin30/train'
test_data_dir = './margin30/test/'
train_generator = train_datagen.flow_from_directory(
train_data_dir,
target_size=(224, 224),
batch_size=32,
class_mode='binary')
test_generator = test_datagen.flow_from_directory(
test_data_dir,
target_size=(224, 224),
batch_size=32,
class_mode='binary')
train_steps = len(glob.glob('./margin30/train/man/*'))
validation_steps = len(glob.glob('./margin30/test/man/*'))
epochs = 100
history = model.fit_generator(
train_generator,
steps_per_epoch=train_steps,
epochs=epochs,
validation_data=test_generator,
validation_steps=validation_steps,
callbacks=[tb_cb]
)
model.save('margin20_close_100.hdf5')