通过Fashion MNIST建立卷积神经网络
我们知道了如何通过Fashion MNIST数据集构建DNN神经网络模型;
这一次,我们仍然使用Fashion MNIST数据集,一起来看一下卷积神经网络模型的构建。
一、卷积神经网络
1.简介
下面简单介绍一下卷积神经网络(Conventional Neural Network,CNN)。
CNN被用于图像识别,语音识别等各种场合,在图像识别的比赛中,基于深度学习的方法几乎都以CNN为基础。
CNN和之前介绍的神经网络大致一样,不过CNN中新出现了卷积层(Convolution层)和池化层(Pooling层)。
2.卷积层
卷积过程大致如下图所示,卷积运算对输入数据应用滤波器。下图的滤波器(有的文献也会用“核”这个词来表示)大小为(3,3),卷积运算以一定间隔滑动滤波器窗口并应用。将各位置滤波器元素和输入的对应元素相乘,然后再求和(有时候也将这个计算过程叫做乘积累加计算)。
然后,将这个结果保存到输出的对应位置。将这个过程在所有位置都进行一遍,就可以得到卷积运算的输出。
3.池化层
池化是缩小高、长方向上的运算。比如下图就是将3*3区域集约成1个元素的处理,缩小空间大小。这里的方法是Max Pooling(从目标区域取出最大值),当然还有Average池化等等。
池化层与卷积层不同,没有要学习的参数,并且通道数也不发生改变。
二、卷积神经网络模型实现
1.模型的构建
相对于通过Fashion MNIST数据集构建DNN神经网络模型例子中代码,我们只需在model建立的层上修改即可。
通过下列代码我们可以看出多增加了两层卷积层keras.layers.Conv2D()与两层池化层keras.layers.MaxPooling2D()。
- 第一层卷积层我们设定了64个大小为(3,3)的滤波器,激活函数为ReLU,然后定义好输入数据的尺寸为(28,28,1);
- 第一层池化层我们将其设定为进行2*2的Max池化;
- 第二层卷积层我们仍设定了64个大小为(3,3)的滤波器,激活函数仍为ReLU;
- 第二层池化层也和第一层池化层一致。
- Flatten层以及其之后的层与DNN实现该模型的层一致。
代码如下:
model=keras.models.Sequential([
keras.layers.Conv2D(64,(3,3),activation='relu',input_shape=(28,28,1)),
keras.layers.MaxPooling2D(2,2),
keras.layers.Conv2D(64,(3,3),activation='relu'),
keras.layers.MaxPooling2D(2,2),
keras.layers.Flatten(),
keras.layers.Dense(128,activation='relu'),
keras.layers.Dense(10,activation='softmax')
])
2.模型的结构
我们一起来看一下这个神经网络的结构
print(model.summary())
输出结果如下所示。可以看出,第一层卷积层输出形状为(,26,26,64),第一层池化层输出形状为(,13,13,64),第二层卷积层输出形状为(,11,11,64),第二层池化层输出形状为(,5,5,64)
这样,我们将train_images通过卷积池化,使其形状变成了(,5,5,64)
这样再进行模型的训练,它的模型拟合程度理论上将会比单纯使用DNN的方法更好。
Model: "sequential_1"
_________________________________________________________________
Layer (type) Output Shape Param #
=================================================================
conv2d_2 (Conv2D) (None, 26, 26, 64) 640
_________________________________________________________________
max_pooling2d_2 (MaxPooling2 (None, 13, 13, 64) 0
_________________________________________________________________
conv2d_3 (Conv2D) (None, 11, 11, 64) 36928
_________________________________________________________________
max_pooling2d_3 (MaxPooling2 (None, 5, 5, 64) 0
_________________________________________________________________
flatten_1 (Flatten) (None, 1600) 0
_________________________________________________________________
dense_2 (Dense) (None, 128) 204928
_________________________________________________________________
dense_3 (Dense) (None, 10) 1290
=================================================================
Total params: 243,786
Trainable params: 243,786
Non-trainable params: 0
_________________________________________________________________
None
3.输出结果及分析
下面给出完整代码:
from tensorflow import keras
import numpy as np
import tensorflow as tf
fashion_mnist=keras.datasets.fashion_mnist
(train_images,train_labels),(test_images,test_labels)=fashion_mnist.load_data()
train_images=train_images/255.0
test_images=test_images/255.0
model=keras.models.Sequential([
keras.layers.Conv2D(64,(3,3),activation='relu',input_shape=(28,28,1)),
keras.layers.MaxPooling2D(2,2),
keras.layers.Conv2D(64,(3,3),activation='relu'),
keras.layers.MaxPooling2D(2,2),
keras.layers.Flatten(),
keras.layers.Dense(128,activation='relu'),
keras.layers.Dense(10,activation='softmax')
])
model.compile(optimizer='adam',loss='sparse_categorical_crossentropy',metrics=['accuracy'])
model.fit(train_images.reshape(-1,28,28,1),train_labels,epochs=5)
print(model.evaluate(test_images.reshape(-1,28,28,1),test_labels))
由于对60000张图片每一张都经过来两层卷积和两层池化,在训练时间上会相对较长一些。
观察下面的结果,相较于DNN的模型,在同样迭代5次后,我们可以看出卷积神经网络模型loss值更小,而accuracy变得相对更大,说明模型更优。
Epoch 1/5
1875/1875 [==============================] - 41s 22ms/step - loss: 0.4377 - accuracy: 0.8404
Epoch 2/5
1875/1875 [==============================] - 39s 21ms/step - loss: 0.2949 - accuracy: 0.8913
Epoch 3/5
1875/1875 [==============================] - 40s 21ms/step - loss: 0.2499 - accuracy: 0.9068
Epoch 4/5
1875/1875 [==============================] - 45s 24ms/step - loss: 0.2171 - accuracy: 0.9193
Epoch 5/5
1875/1875 [==============================] - 42s 22ms/step - loss: 0.1921 - accuracy: 0.9282
313/313 [==============================] - 2s 6ms/step - loss: 0.2532 - accuracy: 0.9059
[0.2532407343387604, 0.9059000015258789]