Train and Evaluate SqueezeNet on Cifar10 Dataset
Imports
from __future__ import absolute_import
from __future__ import division
from __future__ import print_function
import tensorflow as tf
import matplotlib
import matplotlib.pyplot as plt
import numpy as np
datasets = tf.contrib.keras.datasets
layers = tf.contrib.keras.layers
models = tf.contrib.keras.models
losses = tf.contrib.keras.losses
optimizers = tf.contrib.keras.optimizers
metrics = tf.contrib.keras.metrics
preprocessing_image = tf.contrib.keras.preprocessing.image
utils = tf.contrib.keras.utils
callbacks = tf.contrib.keras.callbacks
Load Cifar10 Datset
(x_train, y_train), (x_test, y_test)= datasets.cifar10.load_data()
Image Preprocessing and Augmentation
train_datagen = preprocessing_image.ImageDataGenerator(
rescale=1./255,
shear_range=0.1,
zoom_range=0.1,
horizontal_flip=True)
test_datagen = preprocessing_image.ImageDataGenerator(rescale=1./255)
One Hot Encoding of Target Vector
y_train = utils.to_categorical(y_train, num_classes=10)
y_test = utils.to_categorical(y_test, num_classes=10)
Data Generator
train_generator = train_datagen.flow(x=x_train, y=y_train, batch_size=32, shuffle=True)
test_generator = test_datagen.flow(x=x_test, y=y_test, batch_size=32, shuffle=True)
SqueezeNet Model
def fire_module(x, fire_id, squeeze=16, expand=64):
sq1x1 = "squeeze1x1"
exp1x1 = "expand1x1"
exp3x3 = "expand3x3"
relu = "relu_"
s_id = 'fire' + str(fire_id) + '/'
channel_axis = 3
x = layers.Convolution2D(squeeze, (1, 1), padding='valid', name=s_id + sq1x1)(x)
x = layers.Activation('relu', name=s_id + relu + sq1x1)(x)
left = layers.Convolution2D(expand, (1, 1), padding='valid', name=s_id + exp1x1)(x)
left = layers.Activation('relu', name=s_id + relu + exp1x1)(left)
right = layers.Convolution2D(expand, (3, 3), padding='same', name=s_id + exp3x3)(x)
right = layers.Activation('relu', name=s_id + relu + exp3x3)(right)
x = layers.concatenate([left, right], axis=channel_axis, name=s_id + 'concat')
return x
def SqueezeNet(input_shape=(32,32,3), classes=10):
img_input = layers.Input(shape=input_shape)
x = layers.Convolution2D(64, (3, 3), strides=(2, 2), padding='valid', name='conv1')(img_input)
x = layers.Activation('relu', name='relu_conv1')(x)
# x = layers.MaxPooling2D(pool_size=(3, 3), strides=(2, 2), name='pool1')(x)
x = fire_module(x, fire_id=2, squeeze=16, expand=64)
x = fire_module(x, fire_id=3, squeeze=16, expand=64)
x = layers.MaxPooling2D(pool_size=(3, 3), strides=(2, 2), name='pool3')(x)
x = fire_module(x, fire_id=4, squeeze=32, expand=128)
x = fire_module(x, fire_id=5, squeeze=32, expand=128)
x = layers.Dropout(0.5, name='drop9')(x)
x = layers.Convolution2D(classes, (1, 1), padding='valid', name='conv10')(x)
x = layers.Activation('relu', name='relu_conv10')(x)
x = layers.GlobalAveragePooling2D()(x)
out = layers.Activation('softmax', name='loss')(x)
model = models.Model(img_input, out, name='squeezenet')
return model
Compile Model
def compile_model(model):
# loss
loss = losses.categorical_crossentropy
# optimizer
optimizer = optimizers.RMSprop(lr=0.0001)
# metrics
metric = [metrics.categorical_accuracy, metrics.top_k_categorical_accuracy]
# compile model with loss, optimizer, and evaluation metrics
model.compile(optimizer, loss, metric)
return model
Train Model on Cifar10
sn = SqueezeNet()
sn = compile_model(sn)
history = sn.fit_generator(
train_generator,
steps_per_epoch=400,
epochs=10,
validation_data=test_generator,
validation_steps=200)
Epoch 1/10
400/400 [==============================] - 59s - loss: 2.2349 - categorical_accuracy: 0.1488 - top_k_categorical_accuracy: 0.6128 - val_loss: 2.1264 - val_categorical_accuracy: 0.2295 - val_top_k_categorical_accuracy: 0.7531
Epoch 2/10
400/400 [==============================] - 54s - loss: 2.0378 - categorical_accuracy: 0.2335 - top_k_categorical_accuracy: 0.7801 - val_loss: 1.9289 - val_categorical_accuracy: 0.2762 - val_top_k_categorical_accuracy: 0.8327
Epoch 3/10
400/400 [==============================] - 57s - loss: 1.9405 - categorical_accuracy: 0.2548 - top_k_categorical_accuracy: 0.8183 - val_loss: 1.9037 - val_categorical_accuracy: 0.2917 - val_top_k_categorical_accuracy: 0.8344
Epoch 4/10
400/400 [==============================] - 54s - loss: 1.8825 - categorical_accuracy: 0.2755 - top_k_categorical_accuracy: 0.8338 - val_loss: 1.8343 - val_categorical_accuracy: 0.2914 - val_top_k_categorical_accuracy: 0.8531
Epoch 5/10
400/400 [==============================] - 55s - loss: 1.8404 - categorical_accuracy: 0.2909 - top_k_categorical_accuracy: 0.8469 - val_loss: 1.8556 - val_categorical_accuracy: 0.3044 - val_top_k_categorical_accuracy: 0.8396
Epoch 6/10
400/400 [==============================] - 67s - loss: 1.8109 - categorical_accuracy: 0.3133 - top_k_categorical_accuracy: 0.8521 - val_loss: 1.7528 - val_categorical_accuracy: 0.3272 - val_top_k_categorical_accuracy: 0.8736
Epoch 7/10
400/400 [==============================] - 55s - loss: 1.7910 - categorical_accuracy: 0.3205 - top_k_categorical_accuracy: 0.8558 - val_loss: 1.7415 - val_categorical_accuracy: 0.3412 - val_top_k_categorical_accuracy: 0.8720
Epoch 8/10
400/400 [==============================] - 55s - loss: 1.7703 - categorical_accuracy: 0.3304 - top_k_categorical_accuracy: 0.8655 - val_loss: 1.9308 - val_categorical_accuracy: 0.3233 - val_top_k_categorical_accuracy: 0.8170
Epoch 9/10
400/400 [==============================] - 55s - loss: 1.7438 - categorical_accuracy: 0.3446 - top_k_categorical_accuracy: 0.8690 - val_loss: 1.6670 - val_categorical_accuracy: 0.3596 - val_top_k_categorical_accuracy: 0.8911
Epoch 10/10
400/400 [==============================] - 61s - loss: 1.7154 - categorical_accuracy: 0.3483 - top_k_categorical_accuracy: 0.8788 - val_loss: 1.6629 - val_categorical_accuracy: 0.3811 - val_top_k_categorical_accuracy: 0.8912
Plot Accuracy and Loss Over Time
def plot_accuracy_and_loss(history):
plt.figure(1, figsize= (15, 10))
# plot train and test accuracy
plt.subplot(221)
plt.plot(history.history['categorical_accuracy'])
plt.plot(history.history['val_categorical_accuracy'])
plt.title('SqueezeNet accuracy')
plt.ylabel('accuracy')
plt.xlabel('epoch')
plt.legend(['train', 'test'], loc='upper left')
# plot train and test loss
plt.subplot(222)
plt.plot(history.history['loss'])
plt.plot(history.history['val_loss'])
plt.title('SqueezeNet loss')
plt.ylabel('loss')
plt.xlabel('epoch')
plt.legend(['train', 'test'], loc='upper right')
plt.show()
plot_accuracy_and_loss(history)
Save Model Configuration and Weights
# save model architecture
model_json = sn.to_json()
open('squeeze_net_model.json', 'w').write(model_json)
# save model's learned weights
sn.save_weights('image_classifier_squeeze_net.h5', overwrite=True)
Next Lesson
ResNet: Residual Learning for Image Recognition
Last updated