西瓜味的苹果 发表于 2020-12-30 13:50:01

卷积神经网络0-9数字识别

import tensorflow as tf
from tensorflow.examples.tutorials.mnist import input_data
import numpy as np
from PIL import Image

#算法超参数
batch_size=100
training_epochs=10
learning_rate_init=0.01
display_step=100

#网络参数
n_input=784
n_classes=10

#根据指定的维数返回指定的权数
def WeightsVariable(shape,name_str,stddev=0.1):
    """
    :param shape:               形状,n行n列
    :param name_str:            变量名称
    :param stddev:            正态分布标准差
    :return:
    """
    initial=tf.random_normal(shape=shape,stddev=stddev,dtype=tf.float32)
    return tf.Variable(initial_value=initial,dtype=tf.float32,name=name_str)

#根据指定维数返回指定的偏置
def BiasesVariable(shape,name_str,stddev=0.1):
    """
    :param shape:               偏置的形状,nxn
    :param name_str:            变量名称
    :param stddev:            正态分布标准差
    :return:
    """
    initial=tf.random_normal(shape=shape,stddev=stddev,dtype=tf.float32)
    return tf.Variable(initial_value=initial,dtype=tf.float32,name=name_str)

#二维卷积层的封装(conv2d+bias)
def Conv2d(X,w,b,stride=1,padding="SAME"):
    """
    :param X:                   特征图输入n*n*None
    :param w:                   滤波器(权重参数)
    :param b:                   修正(偏置参数)
    :param stride:            滑动步长(默认为1)
    :param padding:             外填充
    :return:
    """
    with tf.name_scope("Conv2d"):
      y=tf.nn.conv2d(X,w,strides=,padding=padding)
      y=tf.nn.bias_add(y,b)
      return y

#非线性激活层的封装
def Activation(x,activation=tf.nn.relu,name="relu"):
    """
    :param x:                   特征图输入
    :param activation:          激活函数,类似于看待事物的一种模式
    :param name:                名称
    :return:
    """
    with tf.name_scope(name):
      y=activation(x)
      return y

#最大池化层的封装
def Pool2d(x,pool=tf.nn.max_pool,k=2,stride=2):
    return pool(x,ksize=,strides=,padding="VALID")

#全连接层封装
def FullyConnect(x,w,b,activate=tf.identity,act_name="identity"):
    with tf.name_scope("Wx_b"):
      y=tf.add(tf.matmul(x,w),b)
    with tf.name_scope("SoftMax"):
      y=tf.nn.softmax(logits=y)
    with tf.name_scope(act_name):
      y=activate(y)
    return y

#通用的评估函数,用来评估模型在给定的数据集上的损失和准确率
def EvaluateMode10nDataset(sess,images,labels):
    n_samples=images.shape#传入的样本数量
    per_batch_size=batch_size
    loss=0
    acc=0
    if(n_samples<=per_batch_size):
      batch_count=1
      loss,acc=sess.run(,
                        feed_dict={X_origin:images,
                                     Y_true:labels,
                                     learning_rate:learning_rate_init})
    else:
      batch_count=int(n_samples/per_batch_size)
      batch_start=0
      for idx in range(batch_count):
            batch_loss,batch_acc=sess.run(,
                                          feed_dict={X_origin:images,
                                                   Y_true:labels,
                                                   learning_rate:learning_rate_init})
            batch_start+=per_batch_size
            #累计所有批次上的损失和准确率
            loss+=batch_loss
            acc+=batch_acc
    return loss/batch_count,acc/batch_count

'''计算图绘制'''
with tf.Graph().as_default():
    #输入层:28*28*1
    with tf.name_scope("Input"):
      X_origin=tf.placeholder(tf.float32,shape=,name="X_origin")
      Y_true=tf.placeholder(tf.float32,shape=,name="Y_true")
      X_image=tf.reshape(X_origin,[-1,28,28,1],name="X_image")

    #前向推断过程
    with tf.name_scope("Inference"):

      #卷积层第一层:24*24*16
      with tf.name_scope("Conv2d_1"):
            weight_1=WeightsVariable(shape=,name_str="weight_1")
            bias_1=BiasesVariable(shape=,name_str="bias_1")
            conv1_out=Conv2d(X_image,weight_1,bias_1,stride=1,padding="VALID")

      #非线性激活层
      with tf.name_scope("Active"):
            activation_out=Activation(x=conv1_out,activation=tf.nn.relu,name="relu")

      #池化层(默认采用最大池化)12*12*16
      with tf.name_scope("Pool2d_1"):
            pool1_out=Pool2d(x=activation_out,pool=tf.nn.max_pool,k=2,stride=2)

      #将二维特征图转变为1维,2304
      with tf.name_scope("FeatsReshape"):
            features=tf.reshape(pool1_out,[-1,12*12*16])

      #全连接层
      with tf.name_scope("FC_linear1"):
            weight_fc=WeightsVariable(shape=,name_str="weight_fc")
            bias_fc=BiasesVariable(shape=,name_str="bias_fc")
            Ypre_logits=FullyConnect(features,weight_fc,bias_fc,activate=tf.identity,act_name="identity")

    #定义损失层
    with tf.name_scope("Loss"):
      cross_entropy_loss = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(
            labels=Y_true, logits=Ypre_logits
      ))

    #定义训练优化层
    with tf.name_scope("Train"):
      global_step = tf.Variable(0, name='global_step', trainable=False)
      learning_rate=tf.placeholder(tf.float32)
      optimizer=tf.train.AdamOptimizer(learning_rate=learning_rate)
      trainer=optimizer.minimize(cross_entropy_loss,global_step=global_step)

    #定义模型评估层
    with tf.name_scope("Evaluate"):
      correct_pred=tf.equal(tf.argmax(Ypre_logits,1),tf.argmax(Y_true,1))
      accuracy=tf.reduce_mean(tf.cast(correct_pred,tf.float32))

    #定义初始化所有变量节点
    init=tf.initialize_all_variables()

    print("将计算图写入log事件文件中,并在tensorboard中查看!!")
    writer=tf.summary.FileWriter("logs/",graph=tf.get_default_graph())
    writer.close()

    # 导入mnist数据集
    mnist=input_data.read_data_sets("MNIST_data/",one_hot=True)

    '''启动会话'''
    with tf.Session() as sess:
      sess.run(init)                  #初始化variable变量
      total_batches=int(mnist.train.num_examples/batch_size)
      print("每批次的样本数量:",batch_size)
      print("总共的批次数量:",total_batches)
      print("总共的训练数据:",mnist.train.num_examples)

      #保存和载入网络
      saver=tf.train.Saver()
      checkpoint=tf.train.get_checkpoint_state("saver_network")
      if checkpoint and checkpoint.model_checkpoint_path:
            saver.restore(sess,checkpoint.model_checkpoint_path)
            print("Successfully loaded:", checkpoint.model_checkpoint_path)
      else:
            print("Could not find old network weights")

      training_step=0             #记录模型被训练的步数

      #指定训练轮数,将所有的样本都训练一遍
      for epoch in range(training_epochs):
            #把一轮所有的batch都跑一遍
            for batch_idx in range(total_batches):
                # 取出数据
                batch_x, batch_y = mnist.train.next_batch(batch_size)
                #训练优化器训练节点
                sess.run(trainer,feed_dict={
                  X_origin:batch_x,
                  Y_true:batch_y,
                  learning_rate:learning_rate_init,
                })

                #每调用一次训练节点,training_step就加1
                training_step=training_step+1

                # 每训练display_step次,就计算当前模型的损失和准确率
                if training_step % display_step == 0:
                  start_idx = max(0, (batch_idx - display_step) * batch_size)
                  end_idx = batch_idx * batch_size
                  train_loss, train_acc = EvaluateMode10nDataset(sess,
                                                                   mnist.train.images,
                                                                   mnist.train.labels)
                  print("Training Step:" + str(training_step) +
                        ",Training_Loss={:.6f}".format(train_loss) +
                        ",Training_accuracy={:.5f}".format(train_acc))

                  # 计算当前模型在验证集上的损失和准确率
                  validation_loss, validation_acc = EvaluateMode10nDataset(sess,
                                                                           mnist.validation.images,
                                                                           mnist.validation.labels)
                  print("Training Step:" + str(training_step) +
                        ",Validation_Loss={:.6f}".format(validation_loss) +
                        ",Validation_accuracy={:.5f}".format(validation_acc))

                if training_step%display_step==0:
                  saver.save(sess,"./saver_network/check_mnist",global_step=global_step)

      print("训练完毕!!!")

      img = Image.open("5.png")
      img = img.convert('L')# 灰度化
      img = np.reshape(img, (784, 1)).reshape(1, 784)
      img = ((255 - np.array(img, dtype=np.uint8)) / 255.0).reshape(1, 784)
      logits=sess.run(Ypre_logits,feed_dict={
            X_origin:img
      })
      print("预测的图像数字为:",np.argmax(logits))

if __name__ == '__main__':
    pass

西瓜味的苹果 发表于 2020-12-30 13:53:31

因为gui界面功能尚未完善,因此将主要逻辑上传至此(可以运行),后续持续更新代码完善

tryhi 发表于 2020-12-30 16:45:47

高手啊

江晓夜 发表于 2021-1-9 15:13:48

为什么我运行提示没有名叫“tensorflow.examples”的模块

西瓜味的苹果 发表于 2021-1-12 22:09:14

江晓夜 发表于 2021-1-9 15:13
为什么我运行提示没有名叫“tensorflow.examples”的模块

因为你用的2.0,要用1.0的版本
页: [1]
查看完整版本: 卷积神经网络0-9数字识别