1. 数据集简介
2. Lenet 简介
3. 代码实现
3.1 cifar10.py
3.2 cifar10_input.py
3.3 LeNet_inference.py
# _*_ coding: utf-8 _*_
import tensorflow as tf
# 配置神经网络的参数
batch_size = 128
INPUT_NODE = 784
OUTPUT_NODE = 10
IMAGE_SIZE = 24 # cifar数据集裁剪后的图像尺寸为24
NUM_CHANNELS = 3 #原值是1
NUM_LABELS = 10
# 第一个卷积层的尺寸和深度
CONV1_DEEP = 64 # 32 原:6
CONV1_SIZE = 5
# 第二个卷积层的尺寸和深度
CONV2_DEEP = 64 #64 原:16
CONV2_SIZE = 5
# 全连接层的节点个数
FC_SIZE = 120
FC_SIZE_2 = 84
FC_SIZE_3 = 10
# 使用正太分布初始化权重并添加L2正则化,使用w1控制L2损失的大小
def variable_with_weight_loss(shape, stddev, w1):
# 从截断的(2个标准差以内)正态分布中输出随机值
var = tf.Variable(tf.truncated_normal(shape, stddev=stddev))
if w1 is not None:
# l2_loss(var)*w1
weight_loss = tf.multiply(tf.nn.l2_loss(var), w1, name='weight_loss')
# 使用默认图
tf.add_to_collection('losses', weight_loss)
return var
# 定义卷积神经网络的前向传播过程。这里添加了一个新的参数train,用于区别训练过程和测试过程。在这个程序中将用到dropout方法
# dropout可以进一步提升模型可靠性并防止过拟合(dropout过程只在训练时使用)
def inference(input_tensor, train, regularizer):
with tf.variable_scope('layer1-conv1'):
conv1_weights = tf.get_variable('weight', [CONV1_SIZE, CONV1_SIZE, NUM_CHANNELS, CONV1_DEEP],
initializer=tf.truncated_normal_initializer(stddev=0.1))
conv1_biases = tf.get_variable('bias', [CONV1_DEEP],
initializer=tf.constant_initializer(0.0))
conv1 = tf.nn.conv2d(input_tensor, conv1_weights, strides=[1, 1, 1, 1], padding='SAME')
relu1 = tf.nn.relu(tf.nn.bias_add(conv1, conv1_biases))
with tf.name_scope('layer2-pool1'):
pool1 = tf.nn.max_pool(relu1, ksize=[1, 2, 2, 1], strides=[1, 2, 2, 1], padding='SAME')
# 使用LRN对结果进行处理-Local Response Normalization-本地响应标准化
# 增强大的抑制小的,增强泛化能力
norm1 = tf.nn.lrn(pool1, 4, bias=1.0, alpha=0.001 / 9.0, beta=0.75)
with tf.variable_scope('layer3-conv2'):
conv2_weights = tf.get_variable('weight', [CONV2_SIZE, CONV2_SIZE, CONV1_DEEP, CONV2_DEEP],
initializer=tf.truncated_normal_initializer(stddev=0.1))
conv2_biases = tf.get_variable('bias', [CONV2_DEEP],
initializer=tf.constant_initializer(0.0))
conv2 = tf.nn.conv2d(norm1,conv2_weights, strides=[1, 1, 1, 1], padding='SAME')
relu2 = tf.nn.relu(tf.nn.bias_add(conv2, conv2_biases))
with tf.name_scope('layer4-pool2'):
pool2 = tf.nn.max_pool(relu2, ksize=[1, 2, 2, 1], strides=[1, 2, 2, 1], padding='SAME')
# 全连接层
# 将样本变成一维向量
reshaped = tf.reshape(pool2, [batch_size, -1])
# 数据扁平化后的长度
dim = reshaped.get_shape()[1].value
with tf.variable_scope('layer5-fc1'):
fc1_weights = tf.get_variable('weight', [dim, FC_SIZE],
initializer=tf.truncated_normal_initializer(stddev=0.1))
if regularizer != None:
tf.add_to_collection('losses', regularizer(fc1_weights))
fc1_biases = tf.get_variable('bias', [FC_SIZE],
initializer=tf.constant_initializer(0.0))
fc1 = tf.nn.relu(tf.matmul(reshaped, fc1_weights) + fc1_biases)
#if train:
# fc1 = tf.nn.dropout(fc1, 0.5)
with tf.variable_scope('layer6-fc2'):
fc2_weights = tf.get_variable('weight', [FC_SIZE, FC_SIZE_2],
initializer=tf.truncated_normal_initializer(stddev=0.04))
if regularizer != None:
tf.add_to_collection('losses', regularizer(fc2_weights))
fc2_biases = tf.get_variable('bias', [FC_SIZE_2],
initializer=tf.constant_initializer(0.1))
fc2 = tf.nn.relu(tf.matmul(fc1, fc2_weights) + fc2_biases)
with tf.variable_scope('layer7-fc3'):
fc3_weights = tf.get_variable('weight', [FC_SIZE_2, FC_SIZE_3],
initializer=tf.truncated_normal_initializer(stddev=0.1))
if regularizer != None:
tf.add_to_collection('losses', regularizer(fc3_weights))
fc3_biases = tf.get_variable('bias', [FC_SIZE_3],
initializer=tf.constant_initializer(0.0))
fc3 = tf.nn.softmax(tf.matmul(fc2, fc3_weights) + fc3_biases)
return fc3
3.4 LeNet_train.py
# _*_ coding: utf-8 _*_
import os
import tensorflow as tf
import numpy as np
from tensorflow.examples.tutorials.mnist import input_data
# 加载mnist_inference.py中定义的常量和前向传播的函数
import myLenet.LeNet_inference as LeNet_inference
import myLenet.cifar10 as cifar10
import myLenet.cifar10_input as cifar10_input
# 配置神经网络的参数
BATCH_SIZE = 128
batch_size = 128
LEARNING_RATE_BASE = 0.01 #0.8 #
LEARNING_RATE_DECAY = 0.0005 # 0.99
REGULARAZTION_RATE = 0.0001
TRAIN_STEPS = 30000 #3000
MOVING_AVERAGE_DECAY = 0.99
MODEL_SAVE_PATH = "./model/"
MODEL_NAME = "model3.ckpt"
# 下载DIFAR-10数据的默认路径
data_dir = 'C:/Users/xpb/PycharmProjects/MachineVison3/cifar10_data/cifar-10-batches-bin'
def train():
# 从Alex的网站下载并解压到默认位置,需要到cifar10.py修改文件下载的位置
#cifar10.maybe_download_and_extract()
# 使用Reader操作构造CIFAR训练需要的数据(特征及其对应的label)
# 并对数据进行了数据增强(水平翻转/随机对比度亮度/随机裁剪)以及数据的标准化
print("数据读取开始!")
images_train, labels_train = cifar10_input.distorted_inputs(data_dir=data_dir, batch_size=batch_size)
# 使用Reader操作构建CIFAR评估的输入(裁剪图像中间24*24大小的块并进行数据标准化)
images_test, labels_test = cifar10_input.inputs(eval_data=True, data_dir=data_dir, batch_size=batch_size)
onehot_labels = tf.one_hot(labels_train, depth=10, axis=-1)
print("数据读取完成!")
# 输入图像占位符(24*24 3通道)
image_holder = tf.placeholder(tf.float32, [batch_size, 24, 24, 3], name='image_holder')
# 输入标签占位符
label_holder = tf.placeholder(tf.int32, [batch_size], name='y-input')
#label_holder = tf.placeholder(tf.int32, [batch_size, LeNet_inference.OUTPUT_NODE], name='y-input')
regularizer = tf.contrib.layers.l2_regularizer(REGULARAZTION_RATE)
y = LeNet_inference.inference(image_holder, train, regularizer)
# 假如需要保存y,以便在预测时使用
tf.add_to_collection('network-output', y)
global_steps = tf.Variable(0, trainable=False)
#
variable_average = tf.train.ExponentialMovingAverage(MOVING_AVERAGE_DECAY, global_steps)
variable_average_op = variable_average.apply(
tf.trainable_variables())
#cross_entropy = tf.nn.sparse_softmax_cross_entropy_with_logits(labels=tf.argmax(label_holder, 1), logits=y)
labels = tf.cast(label_holder, tf.int64)
cross_entropy = tf.nn.sparse_softmax_cross_entropy_with_logits(logits=y,labels=labels)
cross_entropy_mean = tf.reduce_mean(cross_entropy)
loss = cross_entropy_mean + tf.add_n(tf.get_collection('losses'))
# 将logits节点label_holder和传入loss函数获得最终的loss
#学习率(learning rate)控制着参数的更新速度:此处为指数衰减法
learning_rate = tf.train.exponential_decay(LEARNING_RATE_BASE,
global_step=global_steps, decay_steps=(50000) / BATCH_SIZE,
decay_rate=LEARNING_RATE_DECAY)
#优化器:梯度下降 minimize()函数处理了梯度计算和参数更新两个操作 AdamOptimize
#train_step = tf.train.GradientDescentOptimizer(0.001).minimize(loss, global_step=global_steps)
train_step = tf.train.AdamOptimizer(1e-3).minimize(loss, global_step=global_steps)
with tf.control_dependencies([train_step, variable_average_op]):
# with tf.control_dependencies([train_step]):
train_op = tf.no_op(name='train')
saver = tf.train.Saver()
# 创建默认的session()
sess = tf.InteractiveSession()
#with tf.Session() as sess:
tf.global_variables_initializer().run()
# 启动图片数据增强的线程队列
tf.train.start_queue_runners()
print("开始处理!")
for i in range(TRAIN_STEPS):
image_batch, label_batch = sess.run([images_train, labels_train])
_, loss_value, step,yy = sess.run([train_op, loss, global_steps,y],
feed_dict={image_holder: image_batch, label_holder:label_batch})
if i % 10 == 0:
np.set_printoptions(threshold=np.nan)
print("---------预测结果---------")
y_test = np.argmax(yy, 1)
print(y_test[:10])
d = np.argwhere(label_batch != y_test)
print("预测错误数:",len(d))
print("After %d training steps, loss on training"
"batch is %f" % (i, loss_value))
saver.save(sess, os.path.join(MODEL_SAVE_PATH, MODEL_NAME), global_step=global_steps)
def main(argv=None):
train()
if __name__ == '__main__':
tf.app.run()
3.5 LeNet_test.py
from tensorflow.contrib.keras.api.keras.models import load_model
import tensorflow as tf
import numpy as np
import myLenet.cifar10_input as cifar10_input
import myLenet.LeNet_inference as LeNet_inference
data_dir = 'C:/Users/xpb/PycharmProjects/MachineVison3/cifar10_data/cifar-10-batches-bin'
# 训练轮数
max_steps = 3000
batch_size = 128
if __name__ == '__main__':
np.set_printoptions(threshold=np.nan)
# 使用Reader操作构建CIFAR评估的输入(裁剪图像中间24*24大小的块并进行数据标准化)
# 获取测试集的数据
images_test, labels_test = cifar10_input.inputs(eval_data=False, data_dir=data_dir, batch_size=batch_size)
#images_test, labels_test = cifar10_input.distorted_inputs(data_dir=data_dir, batch_size=batch_size)
onehot_labels = tf.one_hot(labels_test, depth=10, axis=-1)
print(type(images_test))
num_examples = 10000
import math
num_iter = int(math.ceil(num_examples / batch_size))
true_count = 0
total_sample_count = num_iter * batch_size
step = 0
# 创建默认的session()
sess = tf.InteractiveSession()
tf.train.start_queue_runners()
#with tf.Session() as sess:
# 载入训练好的模型
saver = tf.train.import_meta_graph('model/model3.ckpt-13691.meta')
saver.restore(sess, tf.train.latest_checkpoint("model/"))
while step < num_iter:
pred = tf.get_collection('network-output')[0]
image_batch, label_batch = sess.run([images_test, labels_test])
onehot_labels_1 = sess.run([onehot_labels])
print(type(image_batch))
graph = tf.get_default_graph()
x = graph.get_operation_by_name('image_holder').outputs[0]
y_ = graph.get_operation_by_name('y-input').outputs[0]
y = sess.run(pred, feed_dict={x: image_batch, y_: label_batch })
step += 1
print("---------真实值---------")
print(label_batch[:10])
print("---------预测结果---------")
y_test = np.argmax(y, 1)
print(y_test[:10])
# print(y_lable)
d = np.argwhere(label_batch != y_test)
print("预测错误数:", len(d))
true_count = true_count +(batch_size-len(d))
# 统计预测正确的图片的数目
precision = true_count / total_sample_count
print('precision @ 1 = %.3f' % precision)
3.6 运行结果
image.png参考资料
[0][CIFAR-10数据集连接 包含获取数据集的代码
[1] Tensorflow深度学习之二十:CIFAR-10数据集介绍
[2] 浅入浅出TensorFlow 4 - 训练CIFAR数据
[3] 在tensorflow上训练cifar10数据集
[4] cifar官网
[5] TensorFlow学习--卷积神经网络训练CIFAR-10数据集很好,训练加测试
[6] TensorFlow入门:第一个机器学习Demo
[7] tensorflow 从入门到上天教程一
[8] TensorFlow学习笔记-实现经典LeNet5模型
[9] # 深度学习(五)基于tensorflow实现简单卷积神经网络Lenet5
[10] Tensorflow深度学习之二十一:LeNet的实现(CIFAR-10数据集)
[11] Tensorflow实例:(卷积神经网络)LeNet-5模型 很详细,很好
[12] 深度学习 CNN卷积神经网络 LeNet-5详解
网友评论