[深度學習-實踐]BP神經網絡的Helloworld(手寫體識別和Fashion_mnist)

前言

原理部分請看這裏 [深度學習-原理]BP神經網絡

Tensorflow2 實現一個簡單的識別衣服的例子

數據集Fashion_mnist,
此數據集包含10類型的衣服
(‘T-shirt/top’, ‘Trouser’, ‘Pullover’, ‘Dress’, ‘Coat’, ‘Sandal’, ‘Shirt’, ‘Sneaker’, ‘Bag’, ‘Ankle boot’)
訓練數據是60000條,大小是28x28
測試數據是10000條, 大小是28x28

看看訓練數據的前25張圖片吧

import tensorflow as tf
import tensorflow.keras as keras

# Helper libraries
import numpy as np
import matplotlib.pyplot as plt
import os

def show_DataSet():
    fashion_mnist = keras.datasets.fashion_mnist

    (train_images, train_labels), (test_images, test_labels) = fashion_mnist.load_data()
    print(train_images.shape)
    print(len(train_labels))
    print(test_images.shape)
    print(len(test_labels))

    class_names = ['T-shirt/top', 'Trouser', 'Pullover', 'Dress', 'Coat',
                   'Sandal', 'Shirt', 'Sneaker', 'Bag', 'Ankle boot']

    plt.figure(figsize=(10, 10))
    for i in range(25):
        plt.subplot(5, 5, i + 1)
        plt.xticks([])
        plt.yticks([])
        plt.grid(False)
        plt.imshow(train_images[i], cmap=plt.cm.binary)
        plt.xlabel(class_names[train_labels[i]])
    plt.show()
if __name__ == '__main__':
	show_DataSet()

執行結果
在這裏插入圖片描述
訓練代碼如下
是用了倆層全連接的


# TensorFlow and tf.keras
import tensorflow as tf
import tensorflow.keras as keras

# Helper libraries
import numpy as np
import matplotlib.pyplot as plt
import os

def fit_dataSet():
    fashion_mnist = keras.datasets.fashion_mnist

    (train_images, train_labels), (test_images, test_labels) = fashion_mnist.load_data()

    model = keras.Sequential([
        keras.layers.Flatten(input_shape=(28, 28)),
        keras.layers.Dense(128, activation='relu'),
        keras.layers.Dense(10)
    ])

    model.compile(optimizer='adam',
                  loss=tf.keras.losses.SparseCategoricalCrossentropy(from_logits=True),
                  metrics=['accuracy'])
    model.fit(train_images, train_labels, epochs=10)

    test_loss, test_acc = model.evaluate(test_images, test_labels, verbose=2)

    print('\nTest accuracy:', test_acc)

    probability_model = tf.keras.Sequential([model,
                                             tf.keras.layers.Softmax()])

    predictions = probability_model.predict(test_images)

    print(predictions[0])
    print(np.argmax(predictions[0]))
    print(test_labels[0])
    plot_image(0, predictions[0], test_labels, test_images)
    plot_value_array(0, predictions[0], test_labels)


def plot_image(i, predictions_array, true_label, img):
    class_names = ['T-shirt/top', 'Trouser', 'Pullover', 'Dress', 'Coat',
                   'Sandal', 'Shirt', 'Sneaker', 'Bag', 'Ankle boot']

    predictions_array, true_label, img = predictions_array, true_label[i], img[i]
    plt.grid(False)
    plt.xticks([])
    plt.yticks([])

    plt.imshow(img, cmap=plt.cm.binary)

    predicted_label = np.argmax(predictions_array)
    if predicted_label == true_label:
        color = 'blue'
    else:
        color = 'red'

    plt.xlabel("{} {:2.0f}% ({})".format(class_names[predicted_label],
                                100*np.max(predictions_array),
                                class_names[true_label]),
                                color=color)
    plt.show()

def plot_value_array(i, predictions_array, true_label):
    predictions_array, true_label = predictions_array, true_label[i]
    plt.grid(False)
    plt.xticks(range(10))
    plt.yticks([])
    thisplot = plt.bar(range(10), predictions_array, color="#777777")
    plt.ylim([0, 1])
    predicted_label = np.argmax(predictions_array)

    thisplot[predicted_label].set_color('red')
    thisplot[true_label].set_color('blue')
    plt.show()

if __name__ == '__main__':
    fit_dataSet()

執行結果
訓練集上0.8341, 測試集上0.8282

57632/60000 [===========================>..] - ETA: 0s - loss: 0.4788 - accuracy: 0.8346
59040/60000 [============================>.] - ETA: 0s - loss: 0.4808 - accuracy: 0.8341
60000/60000 [==============================] - 2s 37us/sample - loss: 0.4810 - accuracy: 0.8341
10000/10000 - 0s - loss: 0.5949 - accuracy: 0.8292
Test accuracy: 0.8292
[5.4345663e-26 2.4194021e-22 0.0000000e+00 1.8774234e-22 0.0000000e+00
 1.9197876e-03 3.0303031e-32 4.0659446e-02 1.0808072e-21 9.5742083e-01]
9
9

在這裏插入圖片描述
在這裏插入圖片描述

用LeNet方法實現手寫體識別(MNIST數據集)-Tensorflow1

MNIST數據集是一個手寫體數據集,數據集中每一個樣本都是一個0-9的手寫數字
大小28X28
訓練數據目錄結構是這樣的
在這裏插入圖片描述
0的目錄裏都是0的圖片,其它數字目錄也是一樣的。
在這裏插入圖片描述
Lenet 模型
在這裏插入圖片描述

from skimage import io, transform
import os
import glob
import numpy as np
import tensorflow as tf

# 將所有的圖片重新設置尺寸爲32*32
w = 32
h = 32
c = 1

# mnist數據集中訓練數據和測試數據保存地址
train_path = "C:/Users/**/ML_worksbase/lenet5/traning/"
test_path = "C:/Users/**/ML_worksbase/lenet5/test/"
model_path = "C:/Users/**/ML_worksbase/lenet5/model_path/"

# 讀取圖片及其標籤函數
def read_image(path):
    label_dir = [path + x for x in os.listdir(path) if os.path.isdir(path + x)]
    images = []
    labels = []
    for index, folder in enumerate(label_dir):
        for img in glob.glob(folder + '/*.jpg'):
            #print("reading the image:%s" % img)
            image = io.imread(img)
            image = transform.resize(image, (w, h, c))
            images.append(image)
            labels.append(index)

    split_number = int(len(labels) * 0.7)

    all_images = np.asarray(images, dtype=np.float32)
    all_labels = np.asarray(labels, dtype=np.int32)

    traning_images = all_images[:split_number]
    traning_labels = all_labels[:split_number]
    test_images = all_images[split_number:]
    test_labels = all_labels[split_number:]

    return traning_images, traning_labels, test_images, test_labels


# 讀取訓練數據及測試數據
train_data, train_label, test_data, test_label = read_image(train_path)


# 打亂訓練數據及測試數據
train_image_num = len(train_data)
train_image_index = np.arange(train_image_num)
np.random.shuffle(train_image_index)
train_data = train_data[train_image_index]
train_label = train_label[train_image_index]

test_image_num = len(test_data)
test_image_index = np.arange(test_image_num)
np.random.shuffle(test_image_index)
test_data = test_data[test_image_index]
test_label = test_label[test_image_index]
tf.compat.v1.reset_default_graph()

tf.compat.v1.disable_eager_execution()

# 搭建CNN
x = tf.compat.v1.placeholder(tf.float32, [None, w, h, c], name='x')
y_ = tf.compat.v1.placeholder(tf.int32, [None], name='y_')


def inference(input_tensor, train, regularizer):
    # 1.input:[batch, in_height, in_width, in_channels]
    # 2.Filter [filter_height, filter_width, in_channels, out_channels]
    # 3.strides
    # 4. padding:string
    # 5.use_cudnn_on_gpu:bool類型,是否使用cudnn加速,默認爲true
    # return feature map
    # 第一層:卷積層,過濾器的尺寸爲5×5,深度爲6,不使用全0補充,步長爲1。
    # 尺寸變化:32×32×1->28×28×6
    with tf.variable_scope('layer1-conv1'):
        conv1_weights = tf.compat.v1.get_variable('weight', [5, 5, c, 6], initializer=tf.compat.v1.truncated_normal_initializer(stddev=0.1))
        conv1_biases = tf.compat.v1.get_variable('bias', [6], initializer=tf.constant_initializer(0.0))
        conv1 = tf.nn.conv2d(input_tensor, conv1_weights, strides=[1, 1, 1, 1], padding='VALID')
        relu1 = tf.nn.relu(tf.nn.bias_add(conv1, conv1_biases))

    # 第二層:池化層,過濾器的尺寸爲2×2,使用全0補充,步長爲2。
    # 尺寸變化:28×28×6->14×14×6
    with tf.name_scope('layer2-pool1'):
        pool1 = tf.nn.max_pool(relu1, ksize=[1, 2, 2, 1], strides=[1, 2, 2, 1], padding='SAME')

    # 第三層:卷積層,過濾器的尺寸爲5×5,深度爲16,不使用全0補充,步長爲1。
    # 尺寸變化:14×14×6->10×10×16
    with tf.variable_scope('layer3-conv2'):
        conv2_weights = tf.compat.v1.get_variable('weight', [5, 5, 6, 16],
                                        initializer=tf.compat.v1.truncated_normal_initializer(stddev=0.1))
        conv2_biases = tf.compat.v1.get_variable('bias', [16], initializer=tf.constant_initializer(0.0))
        conv2 = tf.nn.conv2d(pool1, conv2_weights, strides=[1, 1, 1, 1], padding='VALID')
        relu2 = tf.nn.relu(tf.nn.bias_add(conv2, conv2_biases))

    # 第四層:池化層,過濾器的尺寸爲2×2,使用全0補充,步長爲2。
    # 尺寸變化:10×10×6->5×5×16
    with tf.variable_scope('layer4-pool2'):
        pool2 = tf.nn.max_pool(relu2, ksize=[1, 2, 2, 1], strides=[1, 2, 2, 1], padding='SAME')

    # 將第四層池化層的輸出轉化爲第五層全連接層的輸入格式。第四層的輸出爲5×5×16的矩陣,然而第五層全連接層需要的輸入格式
    # 爲向量,所以我們需要把代表每張圖片的尺寸爲5×5×16的矩陣拉直成一個長度爲5×5×16的向量。
    # 舉例說,每次訓練64張圖片,那麼第四層池化層的輸出的size爲(64,5,5,16),拉直爲向量,nodes=5×5×16=400,尺寸size變爲(64,400)
    pool_shape = pool2.get_shape().as_list()
    nodes = pool_shape[1] * pool_shape[2] * pool_shape[3]
    reshaped = tf.reshape(pool2, [-1, nodes])

    # 第五層:全連接層,nodes=5×5×16=400,400->120的全連接
    # 尺寸變化:比如一組訓練樣本爲64,那麼尺寸變化爲64×400->64×120
    # 訓練時,引入dropout,dropout在訓練時會隨機將部分節點的輸出改爲0,dropout可以避免過擬合問題。
    # 這和模型越簡單越不容易過擬合思想一致,和正則化限制權重的大小,使得模型不能任意擬合訓練數據中的隨機噪聲,以此達到避免過擬合思想一致。
    # 本文最後訓練時沒有采用dropout,dropout項傳入參數設置成了False,因爲訓練和測試寫在了一起沒有分離,不過大家可以嘗試。
    with tf.variable_scope('layer5-fc1'):
        fc1_weights = tf.compat.v1.get_variable('weight', [nodes, 120], initializer=tf.compat.v1.truncated_normal_initializer(stddev=0.1))
        if regularizer != None:
            tf.add_to_collection('losses', regularizer(fc1_weights))
        fc1_biases = tf.compat.v1.get_variable('bias', [120], initializer=tf.constant_initializer(0.1))
        fc1 = tf.nn.relu(tf.matmul(reshaped, fc1_weights) + fc1_biases)
        if train:
            fc1 = tf.nn.dropout(fc1, 0.5)

    # 第六層:全連接層,120->84的全連接
    # 尺寸變化:比如一組訓練樣本爲64,那麼尺寸變化爲64×120->64×84
    with tf.variable_scope('layer6-fc2'):
        fc2_weights = tf.compat.v1.get_variable('weight', [120, 84], initializer=tf.compat.v1.truncated_normal_initializer(stddev=0.1))
        if regularizer != None:
            tf.add_to_collection('losses', regularizer(fc2_weights))
        fc2_biases = tf.compat.v1.get_variable('bias', [84], initializer=tf.compat.v1.truncated_normal_initializer(stddev=0.1))
        fc2 = tf.nn.relu(tf.matmul(fc1, fc2_weights) + fc2_biases)
        if train:
            fc2 = tf.nn.dropout(fc2, 0.5)

    # 第七層:全連接層(近似表示),84->10的全連接
    # 尺寸變化:比如一組訓練樣本爲64,那麼尺寸變化爲64×84->64×10。最後,64×10的矩陣經過softmax之後就得出了64張圖片分類於每種數字的概率,
    # 即得到最後的分類結果。
    with tf.variable_scope('layer7-fc3'):
        fc3_weights = tf.compat.v1.get_variable('weight', [84, 10], initializer=tf.compat.v1.truncated_normal_initializer(stddev=0.1))
        if regularizer != None:
            tf.add_to_collection('losses', regularizer(fc3_weights))
        fc3_biases = tf.compat.v1.get_variable('bias', [10], initializer=tf.compat.v1.truncated_normal_initializer(stddev=0.1))
        logit = tf.matmul(fc2, fc3_weights) + fc3_biases
    return logit


# 正則化,交叉熵,平均交叉熵,損失函數,最小化損失函數,預測和實際equal比較,tf.equal函數會得到True或False,
# accuracy首先將tf.equal比較得到的布爾值轉爲float型,即True轉爲1.,False轉爲0,最後求平均值,即一組樣本的正確率。
# 比如:一組5個樣本,tf.equal比較爲[True False True False False],轉化爲float型爲[1. 0 1. 0 0],準確率爲2./5=40%。
regularizer = tf.contrib.layers.l2_regularizer(0.001)
y = inference(x, False, regularizer)
cross_entropy = tf.nn.sparse_softmax_cross_entropy_with_logits(logits=y, labels=y_)
cross_entropy_mean = tf.reduce_mean(cross_entropy)
loss = cross_entropy_mean + tf.add_n(tf.get_collection('losses'))
train_op = tf.train.AdamOptimizer(0.001).minimize(loss)
correct_prediction = tf.equal(tf.cast(tf.argmax(y, 1), tf.int32), y_)
accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32))


# 每次獲取batch_size個樣本進行訓練或測試
def get_batch(data, label, batch_size):
    for start_index in range(0, len(data) - batch_size + 1, batch_size):
        slice_index = slice(start_index, start_index + batch_size)
        yield data[slice_index], label[slice_index]


m_saver = tf.train.Saver()

# 創建Session會話
with tf.compat.v1.Session() as sess:
    # 初始化所有變量(權值,偏置等)
    sess.run(tf.global_variables_initializer())


    writer = tf.compat.v1.summary.FileWriter("logs/", sess.graph)
    writer.flush()
    writer.close()
    # 將所有樣本訓練10次,每次訓練中以64個爲一組訓練完所有樣本。
    # train_num可以設置大一些。
    train_num = 10
    batch_size = 64
    #batch_size = 5

    for i in range(train_num):
        train_loss, train_acc, batch_num = 0, 0, 0
        for train_data_batch, train_label_batch in get_batch(train_data, train_label, batch_size):
            trainop, err, acc, y_t = sess.run([train_op, loss, accuracy, y],
                                              feed_dict={x: train_data_batch, y_: train_label_batch})
            #print('y_t = ', y_t)
            train_loss += err
            train_acc += acc
            batch_num += 1
        print("train loss:", train_loss / batch_num)
        print("train acc:", train_acc / batch_num)
        m_saver.save(sess, model_path + "/model_name", global_step=i)

        test_loss, test_acc, batch_num = 0, 0, 0
        for test_data_batch, test_label_batch in get_batch(test_data, test_label, batch_size):
            err, acc = sess.run([loss, accuracy], feed_dict={x: test_data_batch, y_: test_label_batch})
            test_loss += err
            test_acc += acc
            batch_num += 1
        print("test loss:", test_loss / batch_num)
        print("test acc:", test_acc / batch_num)

手寫體數字識別用Tensorflow1準確率再99%以上的例子


import math
import tensorflow as tf
from tensorflow.examples.tutorials.mnist import input_data

# 設置一個隨機數種子
tf.set_random_seed(28)

# 數據加載
mnist = input_data.read_data_sets("data/mnist", one_hot=True)

# 手寫數字識別的數據集主要包含三個部分:訓練集(5.5w, mnist.train)、測試集(1w, mnist.test)、驗證集(0.5w, mnist.validation)
# 手寫數字圖片大小是28*28*1像素的圖片(黑白),也就是每個圖片由784維的特徵描述
train_img = mnist.train.images
train_label = mnist.train.labels
test_img = mnist.test.images
test_label = mnist.test.labels
train_sample_number = mnist.train.num_examples

# 打印數據形狀
print(train_img.shape)
print(train_img[0].shape)
print(train_label.shape)
print(test_img.shape)
print(test_label.shape)
print(test_label[0])

# 相關的參數、超參數的設置
# 學習率,一般學習率設置的比較小
learn_rate_base = 0.1
# 每次迭代的訓練樣本數目
batch_size = 64
# 展示信息的間隔大小
display_step = 1

# 輸入樣本維度大小的信息
input_dim = train_img.shape[1]
# 輸出的維度大小
n_classes = train_label.shape[1]

# 模型的構建
# 1、設置輸入輸出數據的佔位符
x = tf.placeholder(tf.float32, shape=[None, input_dim], name='x')
y = tf.placeholder(tf.float32, shape=[None, n_classes], name='y')
learn_rate = tf.placeholder(tf.float32, name='learn_rate')


# 根據給定的迭代批次,更新產生一個學習率的值
def learn_rate_func(epoth):
    return max(0.001, learn_rate_base * (0.9 ** int(epoth / 10)))


# 返回一個對應的變量,w和b
def get_variable(name, shape=None, dtpye=tf.float32, initializer=tf.random_normal_initializer(mean=0, stddev=0.1)):
    return tf.get_variable(name, shape, dtpye, initializer)


# 2. 構建網絡
def le_net(x, y):
    # 1. 輸入層
    with tf.variable_scope('input1'):
        # 將輸入的x的格式轉換爲規定的格式
        # [None, input_dim] -> [None, height, weight, channels]
        net = tf.reshape(x, shape=[-1, 28, 28, 1])
    # 2. 卷積層
    with tf.variable_scope('conv2'):
        # 卷積
        # conv2d(input, filter, strides, padding, use_cudnn_on_gpu=True, data_format="NHWC", name=None) => 卷積的API
        # data_format: 表示的是輸入的數據格式,兩種:NHWC和NCHW,N=>樣本數目,H=>Height, W=>Weight, C=>Channels
        # input:輸入數據,必須是一個4維格式的圖像數據,具體格式和data_format有關
        #        如果data_format是NHWC的時候,input的格式爲: [batch_size, height, weight, channels] => [批次中的圖片數目,圖片的高度,圖片的寬度,圖片的通道數];
        #        如果data_format是NCHW的時候,input的格式爲: [batch_size, channels, height, weight] => [批次中的圖片數目,圖片的通道數,圖片的高度,圖片的寬度]
        # filter: 卷積核,是一個4維格式的數據,shape: [height, weight, in_channels, out_channels] => [窗口的高度,窗口的寬度,輸入的channel通道數(上一層圖片的深度),輸出的通道數(卷積核數目)]
        # strides:步長,是一個4維的數據,每一維數據必須和data_format格式匹配,表示的是在data_format每一維上的移動步長
        #          當格式爲NHWC的時候,strides的格式爲: [batch, in_height, in_weight, in_channels] => [樣本上的移動大小,高度的移動大小,寬度的移動大小,深度的移動大小],要求在樣本上和在深度通道上的移動必須是1;
        #          當格式爲NCHW的時候,strides的格式爲: [batch,in_channels, in_height, in_weight]
        # padding: 只支持兩個參數"SAME", "VALID"
        #          當取值爲SAME的時候,表示進行填充,"在TensorFlow中,如果步長爲1,並且padding爲SAME的時候,經過卷積之後的圖像大小是不變的";
        #          當VALID的時候,表示多餘的特徵會丟棄;
        # 權重w
        net = tf.nn.conv2d(input=net, filter=get_variable('w', [5, 5, 1, 20]), strides=[1, 1, 1, 1], padding='SAME')
        # 加偏置項
        net = tf.nn.bias_add(net, get_variable('b', [20]))
        # 激勵 ReLu
        # tf.nn.relu => max(fetures, 0)
        # tf.nn.relu6 => min(max(fetures,0), 6)
        net = tf.nn.relu(net)
    # 3. 池化
    with tf.variable_scope('pool3'):
        # 和conv2一樣,需要給定窗口大小和步長
        # max_pool(value, ksize, strides, padding, data_format="NHWC", name=None)
        # avg_pool(value, ksize, strides, padding, data_format="NHWC", name=None)
        # 默認格式下:NHWC,value:輸入的數據,必須是[batch_size, height, weight, channels]格式
        # 默認格式下:NHWC,ksize:指定窗口大小,必須是[batch, in_height, in_weight, in_channels], 其中batch和in_channels必須爲1
        # 默認格式下:NHWC,strides:指定步長大小,必須是[batch, in_height, in_weight, in_channels],其中batch和in_channels必須爲1
        # padding: 只支持兩個參數"SAME", "VALID",當取值爲SAME的時候,表示進行填充,;當VALID的時候,表示多餘的特徵會丟棄;
        net = tf.nn.max_pool(value=net, ksize=[1, 2, 2, 1], strides=[1, 2, 2, 1], padding='SAME')
    # 4. 卷積
    with tf.variable_scope('conv4'):
        net = tf.nn.conv2d(input=net, filter=get_variable('w', [5, 5, 20, 50]), strides=[1, 1, 1, 1], padding='SAME')
        net = tf.nn.bias_add(net, get_variable('b', [50]))
        net = tf.nn.relu(net)
    # 5. 池化
    with tf.variable_scope('pool5'):
        net = tf.nn.max_pool(value=net, ksize=[1, 2, 2, 1], strides=[1, 2, 2, 1], padding='SAME')
    # 6. 全連接
    with tf.variable_scope('fc6'):
        # 28 -> 14 -> 7(因爲此時的卷積不改變圖片的大小)
        size = 7 * 7 * 50
        net = tf.reshape(net, shape=[-1, size])
        net = tf.add(tf.matmul(net, get_variable('w', [size, 500])), get_variable('b', [500]))
        net = tf.nn.relu(net)
    # 7. 全連接
    with tf.variable_scope('fc7'):
        net = tf.add(tf.matmul(net, get_variable('w', [500, n_classes])), get_variable('b', [n_classes]))

    return net


# 構建網絡
act = le_net(x, y)

# 構建模型的損失函數
# softmax_cross_entropy_with_logits: 計算softmax中的每個樣本的交叉熵,logits指定預測值,labels指定實際值
cost = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(logits=act, labels=y))

# 使用Adam優化方式比較多
# learning_rate: 要注意,不要過大,過大可能不收斂,也不要過小,過小收斂速度比較慢
train = tf.train.AdadeltaOptimizer(learning_rate=learn_rate).minimize(cost)

# 得到預測的類別是那一個
# tf.argmax:對矩陣按行或列計算最大值對應的下標,和numpy中的一樣
# tf.equal:是對比這兩個矩陣或者向量的相等的元素,如果是相等的那就返回True,反正返回False,返回的值的矩陣維度和A是一樣的
pred = tf.equal(tf.argmax(act, axis=1), tf.argmax(y, axis=1))
# 正確率(True轉換爲1,False轉換爲0)
acc = tf.reduce_mean(tf.cast(pred, tf.float32))

# 初始化
init = tf.global_variables_initializer()

with tf.Session() as sess:
    # 進行數據初始化
    sess.run(init)

    # 模型保存、持久化
    saver = tf.train.Saver()
    epoch = 0
    while True:
        avg_cost = 0
        # 計算出總的批次
        total_batch = int(train_sample_number / batch_size)
        # 迭代更新
        for i in range(total_batch):
            # 獲取x和y
            batch_xs, batch_ys = mnist.train.next_batch(batch_size)
            feeds = {x: batch_xs, y: batch_ys, learn_rate: learn_rate_func(epoch)}
            # 模型訓練
            sess.run(train, feed_dict=feeds)
            # 獲取損失函數值
            avg_cost += sess.run(cost, feed_dict=feeds)

        # 重新計算平均損失(相當於計算每個樣本的損失值)
        avg_cost = avg_cost / total_batch

        # DISPLAY  顯示誤差率和訓練集的正確率以此測試集的正確率
        if (epoch + 1) % display_step == 0:
            print("批次: %03d 損失函數值: %.9f" % (epoch, avg_cost))
            # 這裏之所以使用batch_xs和batch_ys,是因爲我使用train_img會出現內存不夠的情況,直接就會退出
            feeds = {x: train_img[:1000], y: train_label[:1000], learn_rate: learn_rate_func(epoch)}
            train_acc = sess.run(acc, feed_dict=feeds)
            print("訓練集準確率: %.3f" % train_acc)
            feeds = {x: test_img, y: test_label, learn_rate: learn_rate_func(epoch)}
            test_acc = sess.run(acc, feed_dict=feeds)
            print("測試準確率: %.3f" % test_acc)

            # 如果訓練準確率和測試準確率大於等於0.99停止迭代,並保存模型
            if train_acc >= 0.99 and test_acc >= 0.99:
                saver.save(sess, './mnist/model_{}_{}'.format(train_acc, test_acc), global_step=epoch)
                break
        epoch += 1

    # 模型可視化輸出
    writer = tf.summary.FileWriter('./mnist/graph', tf.get_default_graph())
    writer.close()

print("end....")

在這裏插入圖片描述
模型訓練可視化可以下面命令
在這裏插入圖片描述

參考資料

[1] https://blog.csdn.net/Daycym/article/details/90267188

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章