在MNIST数据集上构建一个神经网络,进行训练,以达到良好的识别效果
1 导入模块
首先,导入必要的模块
import numpy as np
import tensorflow as tf
from tensorflow import keras
from keras import models, layers
import matplotlib.pyplot as plt
2 下载数据集
然后,载入MNIST数据集,并进行数据预处理,以适用于训练
# load MNIST dataset
(train_images, train_labels), (test_images, test_labels) = keras.datasets.mnist.load_data()
# train_images: 60000*28*28, train_labels: 60000*1
# test_images: 10000*28*28, test_labels: 10000*1
# pre-process data, change data shape & type
train_input = train_images.reshape(60000,28*28)
train_input = train_input.astype('float32')/255
test_input = test_images.reshape(10000,28*28)
test_input = test_input.astype('float32')/255
train_output = keras.utils.to_categorical(train_labels)
test_output = keras.utils.to_categorical(test_labels)
其中,图片(28,28)二维数据被归一化到784(28*28)的一维数据。以适应神经网络的输入维度。并且0-255之间的灰度图取值归一化到0-1之间的浮点数。输出的类别数据(0-9)转化为分类数据,即0-9的数字转化为长度为10的向量,在对应分类的元素置为1,其它为0。比如
数值5 转化为 [0,0,0,0,0,1,0,0,0,0,0]
3 构造神经网络
然后,搭建神经网络
# build model
network = models.Sequential()
network.add(layers.Dense(512, activation='relu', input_shape=(28*28,)))
network.add(layers.Dense(10, activation='softmax'))
network.compile(optimizer='rmsprop',loss='categorical_crossentropy',metrics=['accuracy'])
#show network summary
network.summary()
这段代码的输出为网络的结构信息,如下
Model: "sequential"
_________________________________________________________________
Layer (type) Output Shape Param #
=================================================================
dense (Dense) (None, 512) 401920
_________________________________________________________________
dense_1 (Dense) (None, 10) 5130
=================================================================
Total params: 407,050
Trainable params: 407,050
Non-trainable params: 0
_________________________________________________________________
为一个由两个全连接层构成的神经网络,第一层的输入为784,输出为512,采用relu激活函数;第二层的输出为10,采用softmax激活函数。输出表示结果分别为0-9数值的概率。
4 训练神经网络
模型的训练调用函数
# train, with batch size and epochs
network.fit(train_input, train_output, epochs=10, batch_size=128)
指定训练的次数(epochs)和每批次的训练数据量(batch_size)。batch_size表示每次取多少数据来进行一次训练。epochs表示进行多少次在输入数据集上的训练。训练产生结果如下
Epoch 1/10
469/469 [==============================] - 3s 2ms/step - loss: 0.2534 - accuracy: 0.9258
Epoch 2/10
469/469 [==============================] - 1s 2ms/step - loss: 0.1030 - accuracy: 0.9690
Epoch 3/10
469/469 [==============================] - 1s 2ms/step - loss: 0.0679 - accuracy: 0.9798
Epoch 4/10
469/469 [==============================] - 1s 2ms/step - loss: 0.0496 - accuracy: 0.9856
Epoch 5/10
469/469 [==============================] - 1s 2ms/step - loss: 0.0373 - accuracy: 0.9886
Epoch 6/10
469/469 [==============================] - 1s 2ms/step - loss: 0.0292 - accuracy: 0.9913
Epoch 7/10
469/469 [==============================] - 1s 2ms/step - loss: 0.0224 - accuracy: 0.9934
Epoch 8/10
469/469 [==============================] - 1s 2ms/step - loss: 0.0174 - accuracy: 0.9946
Epoch 9/10
469/469 [==============================] - 1s 2ms/step - loss: 0.0130 - accuracy: 0.9964
Epoch 10/10
469/469 [==============================] - 1s 2ms/step - loss: 0.0103 - accuracy: 0.9969
列出了每次训练的损失函数值(loss)和准确率(accuracy)。能够达到0.9969。
5 评估神经网络
训练完成后,在测试集上进行评估
# evaluate network performance using test data
network.evaluate(test_input, test_output)
结果如下
313/313 [==============================] - 1s 1ms/step - loss: 0.0735 - accuracy: 0.9806
[0.0734768807888031, 0.9805999994277954]
显示在测试集上的损失函数值和准确率。准确率为0.9806。
这里通过画图显示前100张图片推理结果
# perform prediction on test data
predict_output = network.predict(test_input)
# lines and columns of subplots
m = 10
n = 10
num = m*n
# figure size
plt.figure(figsize=(11,11))
# plot first 100 pictures of test images and results
for i in range(num):
plt.subplot(m,n,i+1)
cmap = 'gray_r' if np.argmax(predict_output[i]) == np.argmax(test_output[i]) else 'gray'
plt.imshow(test_images[i], cmap=cmap)
plt.xticks([])
plt.yticks([])
plt.show()
推理正确的显示为白底的图片,推理错误的显示为黑色背景的图片。运行结果如下
前100张出现1张错误识别的图像。
参考链接:https://blog.csdn.net/weixin_45825073/article/details/121753882