【Tensorflow_DL_Note11】TensorFlow神经网络程序设计框架样例MNIST的训练与测试

# coding=UTF-8
# ========================================================================================================
# 文件说明:
#       [1]LeNet-5模型
#       [2]该文件定义了【神经网络】【前向传播的过程】和【神经网络中的参数】
#       [3]mnist_inference.py
# 开发环境:
#       Win10+Tensorflow+OpenCv3.3+Python3.5+PyCharm5.0.3
# 时间地点:
#       陕西师范大学 文津楼 2018.5.2
# 参考资料:
#       http://www.tensorfly.cn/tfdoc/tutorials/mnist_pros.html
# 涉及的知识点:
#       [1]Tensorflow中的【变量管理机制】
#       [2]tf.get_variable()
#       [3]tf.variable_scope()
# =======================================================================================================
import tensorflow as tf
#========================================================================================================
#函数原型:
#       get_variable(name,shape=None,dtype=None,initializer=None,regularizer=None,trainable=True,collections=None,
#                 caching_device=None,partitioner=None,validate_shape=True,use_resource=None,custom_getter=None,
#                 constraint=None)
#函数说明:
#       [1]创建一个名为name,维度为shape,类型为dtype,初始化值为initializer的Tensorflow变量
#       [2]tf.get_variable()是Tensorflow中的【变量管理函数】
#       [3]当使用tf.get_variable()函数用来获取变量的时候,tf._get_variable()必须与tf.variable_scope()函数互相
#          配合使用
#========================================================================================================
#========================================================================================================
#函数原型:
#       add_to_collection(name, value)
#函数说明:
#       [1]add_to_collection(name,value)为Graph的一个方法
#       [2]可以简单的认为Graph维护了一个字典,其中key为name,value为list,而add_to_collection就是把变量通过对应的
#          key把添加到list中去
#========================================================================================================
#========================================================================================================
#模块说明:
#       定义【神经网络结构】相关的【神经网络参数】
#========================================================================================================
INPUT_NODE  = 784          #[1]神经网络【输入层】的节点数=Img_Width x Img_Height x ImgChannel=28x28x1
OUTPUT_NODE = 10           #[2]神经网络【输出层】的节点数=将要分类的类别数
LAYER1_NODE = 500          #[3]层节点数
#========================================================================================================
#函数说明:
#       创建神经网络中的【权值变量】
#返回值:
#       返回已经创建的权值变量
#========================================================================================================
def get_weight_variable(shape, regularizer):
    weights = tf.get_variable("weights", shape, initializer=tf.truncated_normal_initializer(stddev=0.1))
    if regularizer != None:
        tf.add_to_collection('losses', regularizer(weights))
    return weights

#========================================================================================================
#函数说明:
#       定义神经网络的前向传播过程
#返回值:
#       前向传播的结果
#========================================================================================================
def inference(input_tensor, regularizer):
    with tf.variable_scope('layer1'):
        weights = get_weight_variable([INPUT_NODE, LAYER1_NODE], regularizer)
        biases  = tf.get_variable("biases", [LAYER1_NODE], initializer=tf.constant_initializer(0.0))
        layer1  = tf.nn.relu(tf.matmul(input_tensor, weights) + biases)

    with tf.variable_scope('layer2'):
        weights = get_weight_variable([LAYER1_NODE, OUTPUT_NODE], regularizer)
        biases  = tf.get_variable("biases", [OUTPUT_NODE], initializer=tf.constant_initializer(0.0))
        layer2  = tf.matmul(layer1, weights) + biases

    return layer2

#coding=UTF-8
#========================================================================================================
#文件说明:
#       [1]LeNet-5模型
#       [2]该文件定义了【神经网络】的【训练程序】
#       [3]mnist_train.py
#开发环境:
#       Win10+Tensorflow1.7.0+OpenCv3.3+Python3.5+PyCharm5.0.3
#时间地点:
#       陕西师范大学 文津楼 2018.5.2
#参考资料:
#       http://www.tensorfly.cn/tfdoc/tutorials/mnist_pros.html
#涉及的知识点:
#【学习率】
#       [1]学习率:在训练神经网络的时候,我们需要通过设置【学习率,learning_rate】来【控制】【参数的更新速度】
#       [2]学习率决定了每次每次参数的更新的幅度,如果幅度过大,那么可能导致参数在极优值得两侧来回移动;相反,学习率过低,
#          虽然可以保证收敛,但是这回大大的降低优化的速度
#       [3]因此,学习率的设置不能过大,也不能过低。为了解决【学习率】的这个问题,Tensorflow提供了一种更加灵活的学习率
#          设置方法----【指数衰减法】。tf.train.exponential_decay函数实现了【指数衰减学习率】
#       [4]【指数衰减学习率】:通过这个函数,可以先使用较大的学习率来快速的得到一个比较优的解,然后,随着迭代的继续逐步
#          衰减小学习率,使得模型在训练后更加稳定,该函数涉及三个参数:
#                  [1]learning_rate-----初始学习率
#                  [2]decay_rate--------衰减系数
#                  [3]decay-steps-------衰减速度
#【滑动平均模型】
#       总结一下神经网络优化的七大方法:
#          [1]神经网络的结构
#                 [1]全连接神经网络
#                 [2]串联的卷积神经网络--LeNet-5,AlexNet
#                 [3]并联的卷积神经网络--Inception-V3
#                 [4]全卷机神经网络-----FCN
#                 [5]对抗生成网络-------GAN
#          [2]神经网络的层数
#          [3]损失函数
#                 [1]分类问题------softmax+交叉熵损失
#                 [2]回归问题------均方误差MSE损失函数
#          [4]神经网络优化算法
#                 [1]反向传播算法----针对的是整个神经网络模型在训练数据上的损失函数的优化
#                 [2]梯度下降算法----针对的是单个参数的优化
#          [5]学习率的设置-------指数衰减学习率
#                 [1]基础学习率
#                 [2]当前迭代轮数
#                 [3]总迭代轮数 = 训练样本的总数/每个Batch中的样本数
#                 [4]学习率衰减率
#          [6]过拟合问题---------正则化的损失函数,一般模型的正则化指代的是神经网络参数的正则化,偏置项一般不进行正则化
#          [7]滑动平均模型-------衰减率decay
#========================================================================================================
import os
import mnist_inference
import tensorflow as tf
from   tensorflow.examples.tutorials.mnist import input_data
#========================================================================================================
#模块说明:
#       配置神经网络的参数,训练神经网络的参数
#========================================================================================================
BATCH_SIZE           = 100              #[1]每个批次提供的图像的数量
LEARNING_RATE_BASE   = 0.8              #[2][指数衰减学习率]中的[初始学习率][基础学习率]
LEARNING_RATE_DECAY  = 0.99             #[3][指数衰减学习率]中的[衰减系数][学习率的衰减率]
REGULARIZATION_RATE  = 0.0001           #[4]描述模型复杂程度的正则化项在损失函数中的系数
TRAINING_STEPS       = 30000            #[5]训练的迭代数
MOVING_AVERAGE_DECAY = 0.99             #[6][滑动平均模型]的[衰减率],控制模型更新的速度
MODEL_SAVE_PATH      = "F:/MnistSet/"   #[7]模型保存的路径
MODEL_NAME           = "mnist_model"    #[8]模型的名的前缀mnist_model-29001.meta
#========================================================================================================
#函数说明:
#       配置神经网络的参数,训练神经网络的参数
#========================================================================================================
def train(mnist):
    x  = tf.placeholder(tf.float32, [None, mnist_inference.INPUT_NODE],  name='x-input')
    y_ = tf.placeholder(tf.float32, [None, mnist_inference.OUTPUT_NODE], name='y-input')

    regularizer = tf.contrib.layers.l2_regularizer(REGULARIZATION_RATE)#[1]返回一个正则化生成函数
    y           = mnist_inference.inference(x, regularizer)            #[2]调用前向传播函数
    global_step = tf.Variable(0, trainable=False)                      #[3]定义存储训练轮数的变量,该参数不可优化
                                                            #[1]定义一个滑动平均的类,指定衰减率和num_updates参数
    variable_averages     = tf.train.ExponentialMovingAverage(MOVING_AVERAGE_DECAY, global_step)
                                                            #[2]在所有代表神经网络参数的变量上使用滑动平均
    variables_averages_op = variable_averages.apply(tf.trainable_variables())
                                                            #[3]计算交叉熵,作为刻画预测值和真实值之间差距的损失函数
    cross_entropy         = tf.nn.sparse_softmax_cross_entropy_with_logits(labels=tf.argmax(y_,1),logits=y)
    cross_entropy_mean    = tf.reduce_mean(cross_entropy)   #[4]计算当前batch所有样例的[交叉熵平均值]
                                                            #[5]总损失等于交叉熵损失和正则化损失之和[模型的正则化损失]
    loss                  = cross_entropy_mean + tf.add_n(tf.get_collection('losses'))
                                                            #[6]设置指数衰减学习率
    learning_rate         = tf.train.exponential_decay(LEARNING_RATE_BASE,global_step,
                                              mnist.train.num_examples / BATCH_SIZE, LEARNING_RATE_DECAY,staircase=True)
                                                            #[7]使用优化算法来优化模型的损失函数
    train_step            = tf.train.GradientDescentOptimizer(learning_rate).minimize(loss, global_step=global_step)
                                                            #[8]指定计算图中运算操作的依赖和计算顺序
    with tf.control_dependencies([train_step, variables_averages_op]):
        train_op = tf.no_op(name='train')                   #[9]确保上面的指定的运算操作按照指定的顺序和依赖执行

    saver = tf.train.Saver()                                #[1]定义一个持久化类的类对象saver
    with tf.Session() as sess:                              #[2]创建一个会话Session,并通过python的上下文管理器来管理这个会话
        tf.global_variables_initializer().run()             #[3]使用创建好的会话sess执行Tensorflow的变量初始化操作

        for i in range(TRAINING_STEPS):                     #[1]迭代的训练神经网络
            xs, ys = mnist.train.next_batch(BATCH_SIZE)     #[2]从数据集得到下一轮的训练样本
                                                            #[3]使用会话执行训练过程
            _, loss_value, step = sess.run([train_op, loss, global_step], feed_dict={x: xs, y_: ys})
            if i % 1000 == 0:                               #[4]每1000次,保存一次模型
                                                            #[5]输出当前的训练情况,输出迭代的轮数和模型在当前batch上的损失函数大小
                print('After {0:d} training step(s), loss on training batch is {1:g} '.format(step, loss_value))
                                                            #[6]保存当前的模型,这里给出了global_step参数,这样可以在每个保存模型的文件名尾部加上训练的轮数
                saver.save(sess, os.path.join(MODEL_SAVE_PATH, MODEL_NAME), global_step=global_step)
#========================================================================================================
#模块说明:
#       主程序的入口点
#========================================================================================================
def main(argv=None):
    print('[Info]TensorFlow_Version is',tf.__version__)     #[1]定义处理MNIST数据集的类,这个类在初始化时会自动下载数据
    mnist = input_data.read_data_sets('F:/MnistSet/',one_hot=True)
    train(mnist)                                            #[2]调用train函数进行模型的训练
#========================================================================================================
#模块说明:
#       Tensorflow提供的一个主程序入口,tf.app.run函数将会调用上面的main函数
#========================================================================================================
if __name__ == '__main__':
    tf.app.run()



#coding=UTF-8
#========================================================================================================
#文件说明:
#       [1]LeNet-5模型的测试文件
#       [2]该文件定义了【神经网络】的【训练程序】
#       [3]main.py
#开发环境:
#       Win10+Tensorflow1.7.0+OpenCv3.3+Python3.5+PyCharm5.0.3
#时间地点:
#       陕西师范大学 文津楼 2018.5.4
#参考资料:
#       http://www.tensorfly.cn/tfdoc/tutorials/mnist_pros.html
#涉及的知识点:
#========================================================================================================
import time
import numpy as np
import tensorflow as tf
import tensorflow.examples.tutorials.mnist.input_data as input_data

import mnist_train              #[1]加载mnist_train.py文件中定义的函数和常量
import mnist_inference          #[2]加载mnist_inference.py文件中定义的函数和常量

EVAL_INTERVAL_SECS = 10
#========================================================================================================
#函数说明:
#   网络模型在测试集上的测试,用于网络模型训练和模型质量的评估
#========================================================================================================
def evaluate(mnist):
    with tf.Graph().as_default() as g: #[1]定义一个计算图类Graph的类对象,并创建一个新的计算图g
                                       #[2]为[输入层]和[输出层]定义[两个占位符]
        x                  = tf.placeholder(tf.float32,[None,mnist_inference.INPUT_NODE], name='x-input')
        y_                 = tf.placeholder(tf.float32,[None,mnist_inference.OUTPUT_NODE],name='y-input')
        validate_feed      = {x:mnist.validation.images,y_:mnist.validation.labels}
                                       #[3]直接通过封装好的函数来计算前向传播的结果
        y                  = mnist_inference.inference(x,None)
                                       #[4]使用前向传播的结果,计算正确率.仅仅测试预测值和正确值在第一维度上是否相等
        correct_prediction = tf.equal(tf.argmax(y,1),tf.argmax(y_,1))
                                       #[5]因为上述比较的结果是布尔值,下面首先将布尔值转化为浮点数,然后计算平均值
        accuracy           = tf.reduce_mean(tf.cast(correct_prediction,tf.float32))
                                       #[6]实例化一个滑动平均模型的类对象,这将会使得模型在测试集上更加的健壮(Robust)
        variable_averages  = tf.train.ExponentialMovingAverage(mnist_train.MOVING_AVERAGE_DECAY)
                                       #[7]下面的函数可以直接生成tf.train.Saver所需要的变量重命名字典
        variable_to_restore= variable_averages.variables_to_restore()
                                       #[8]该函数将会保存运行Tensorflow运行所需要的全部信息
        saver              = tf.train.Saver(variable_to_restore)
        #========================================[计算图的定义阶段完毕]=====================================
        #========================================[计算图的执行阶段开始]=====================================
        while True:
            with tf.Session() as sess: #[1]实例化一个会话Session的类对象,并重新命名为sess
                                       #[2]该函数将会通过文件路径找到CheckPoint目录下的最新的模型文件名
                ckpt = tf.train.get_checkpoint_state(mnist_train.MODEL_SAVE_PATH)
                if ckpt and ckpt.model_checkpoint_path:
                                       #[3]加载模型
                    saver.restore(sess,ckpt.model_checkpoint_path)
                                       #[4]通过[文件名]得到[模型保存时迭代的轮数]
                    global_step = ckpt.model_checkpoint_path.split('/')[-1].split('-')[-1]
                                       #[5]执行准确率的计算节点
                    accuracy_score = sess.run(accuracy,feed_dict=validate_feed)
                                       #[6]输出迭代的轮数和准确率
                    print("After %s training steps.validation""accuracy = %g"%(global_step,accuracy_score))
                else:
                    print('No checkpoint file found')
                    return
                time.sleep(EVAL_INTERVAL_SECS)
#========================================================================================================
#模块说明:
#       主程序的入口点
#========================================================================================================
def main(argv=None):
    print('[Info]TensorFlow_Version is',tf.__version__)      #[1]定义处理MNIST数据集的类,这个类在初始化时会自动下载数据
    mnist = input_data.read_data_sets('F:/MnistSet/',one_hot=True)
    mnist_train.train(mnist)
    evaluate(mnist)                                          #[2]调用train函数进行模型的训练
#========================================================================================================
#模块说明:
#       Tensorflow提供的一个主程序入口,tf.app.run函数将会调用上面的main函数
#========================================================================================================
if __name__ == '__main__':
    tf.app.run()
LeNet-5神经网络 C源代码,这个写的比较好,可以用gcc编译去跑,结合理论可以对深度学习有更深刻的了解 介绍 根据YANN LECUN的论文《Gradient-based Learning Applied To Document Recognition》设计的LeNet-5神经网络,C语言写成,不依赖任何第三方库。 MNIST手写字符集初代训练识别率97%,多代训练识别率98%。 DEMO main.c文件为MNIST数据集的识别DEMO,直接编译即可运行,训练集60000张,测试集10000张。 项目环境 该项目为VISUAL STUDIO 2015项目,用VISUAL STUDIO 2015 UPDATE1及以上直接打开即可编译。采用ANSI C编写,因此源码无须修改即可在其它平台上编译。 如果因缺少openmp无法编译,请将lenet.c中的#include和#pragma omp parallel for删除掉即可。 API #####批量训练 lenet: LeNet5的权值的指针,LeNet5神经网络的核心 inputs: 要训练的多个图片对应unsigned char二维数组的数组,指向的二维数组的batchSize倍大小内存空间指针。在MNIST测试DEMO中二维数组为28x28,每个二维数组数值分别为对应位置图像像素灰度值 resMat:结果向量矩阵 labels:要训练的多个图片分别对应的标签数组。大小为batchSize batchSize:批量训练输入图像(二维数组)的数量 void TrainBatch(LeNet5 *lenet, image *inputs, const char(*resMat)[OUTPUT],uint8 *labels, int batchSize); #####单个训练 lenet: LeNet5的权值的指针,LeNet5神经网络的核心 input: 要训练的图片对应二维数组 resMat:结果向量矩阵 label: 要训练的图片对应的标签 void Train(LeNet5 *lenet, image input, const char(*resMat)[OUTPUT],uint8 label); #####预测 lenet: LeNet5的权值的指针,LeNet5神经网络的核心 input: 输入的图像的数据 labels: 结果向量矩阵指针 count: 结果向量个数 return 返回值为预测的结果 int Predict(LeNet5 *lenet, image input, const char(*labels)[LAYER6], int count); #####初始化 lenet: LeNet5的权值的指针,LeNet5神经网络的核心
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值