代码以及详细步骤如下:
#-*- coding:utf-8 _*-
"""
@author:bluesli
@file: CNN-convolutional_neural_network.py
@time: 2018/06/24
"""
'''
总结,要想写好代码就要自己理解卷积的定义,怎样才能卷积,理解他的形状变换,矩阵乘法一定要学好;
卷积神经网络(cnn)与简单神经网络的区别)
1:卷积层2:池化层
data->n*784(是灰度图:28*28*1)->卷积层1(filter(3*3*1)->池化层1(pooling(2*2))->卷积层2-》池化层2-》1024的向量(全连接的第一层)-》真正的输出层(10)
weights = {
'wc1':tf.Variable(tf.random_normal([3,3,1,64],stddec=0,1))#参数说明:h,w,深度,特征图个数
'wc2':tf.Variable(tf.random_normal([3,3,64,64],stddec=0,1))
'wd1':tf.Variable(tf.random_normal([7*7*128,1024],stddec=0,1))
'wd2':tf.Variable(tf.random_normal([1024,10],stddec=0,1))
}
biases = {
'bc1' :tf.Variable(tf.random_normal([64],stddec=0,1))
'bc2':tf.Variable(tf.random_normal([128],stddec=0,1))
'bd1':tf.Variable(tf.random_normal([024],stddec=0,1))#全连接层
'bd2':tf.Variable(tf.random_normal([10],stddec=0,1))
}
卷积和池化的操作:s
这里的tensor是四维的(h,w,d,c),需要对数据进行reshape
第一次池化
conv1 = tf.nn.conv2d(_input_r,_w['wc1'],strides=[1,1,1,1](四维的格式),padding=(SAME自动添加0,valid:则不填充,舍弃不够的数据)推荐使用SAME
激活函数:nn.relu
#池化
#随机去掉一些点,
第二次池化
reshape全连接层的输入
全连接曾的操作,然后dropout
后面的操作就差不多了(变量初始化,构造损失函数,做小化损失,预测,找到精度);
'''
import tensorflow as tf
from tensorflow.examples.tutorials.mnist import input_data
mnist = input_data.read_data_sets('data/',one_hot=True)#此处的one_hot =True必须加上,不然可能会导致,形状有问题,在做矩阵乘法时出错;
train_img = mnist.train.images
train_label = mnist.train.labels
test_img = mnist.test.images
test_label = mnist.test.labels
n_input = 784
n_output = 10
stddev =0.1
weights = {
'wc1':tf.Variable(tf.random_normal([3,3,1,64],stddev=stddev)),
'wc2':tf.Variable(tf.random_normal([3,3,64,128],stddev=stddev)),
'wd1':tf.Variable(tf.random_normal([7*7*128,1024],stddev=stddev)),
'wd2':tf.Variable(tf.random_normal([1024,n_output],stddev=stddev))
}
biases = {
'bc1':tf.Variable(tf.random_normal([64],stddev=stddev)),
'bc2':tf.Variable(tf.random_normal([128],stddev=stddev)),
'bd1':tf.Variable(tf.random_normal([1024],stddev=stddev)),
'bd2':tf.Variable(tf.random_normal([n_output],stddev=stddev))
}
#定义卷积层模型:与一般的神经网络模型多了卷积和池化
def conv_basic(_input,_w,_b,_keepratio):
#改变输入的形状为28*28*1*1
_input_r = tf.reshape(_input,[-1,28,28,1])
# 卷积一层
_conv1 = tf.nn.conv2d(_input_r,_w['wc1'],strides =[1,1,1,1],padding='SAME')
_conv1 = tf.nn.relu(tf.nn.bias_add(_conv1,_b['bc1']))
#池化第一层
_pool1 = tf.nn.max_pool(_conv1,ksize=[1,2,2,1],strides=[1,2,2,1],padding='SAME')
#随机丢弃一些点
_pool_dr1 = tf.nn.dropout(_pool1,_keepratio)
#卷积二层,池化二层
_conv2 = tf.nn.conv2d(_pool_dr1,_w['wc2'],strides=[1,1,1,1],padding='SAME')
_conv2 = tf.nn.relu(tf.nn.bias_add(_conv2,_b['bc2']))
_pool2 = tf.nn.max_pool(_conv2,ksize=[1,2,2,1],strides=[1,2,2,1],padding='SAME')
_pool_dr2 = tf.nn.dropout(_pool2,_keepratio)
#定义全连接层
_dense1 = tf.reshape(_pool_dr2,[-1,weights['wd1'].get_shape().as_list()[0]])
_fc1 = tf.nn.relu(tf.add(tf.matmul(_dense1,_w['wd1']),_b['bd1']))
_fc_dr1 = tf.nn.dropout(_fc1,_keepratio)
_out = tf.add(tf.matmul(_fc_dr1, _w['wd2']), _b['bd2'])
out = {'input_r': _input_r, 'conv1': _conv1, 'pool1': _pool1, 'pool1_dr1': _pool_dr1,
'conv2': _conv2, 'pool2': _pool2, 'pool_dr2': _pool_dr2, 'dense1': _dense1,
'fc1': _fc1, 'fc_dr1': _fc_dr1, 'out': _out
}
return out
x = tf.placeholder(tf.float32,[None,n_input])
y = tf.placeholder(tf.float32,[None,n_output])
keepratio = tf.placeholder(tf.float32)
pred = conv_basic(x,weights,biases,keepratio)['out']
cost = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(logits=pred,labels=y))
optimize = tf.train.GradientDescentOptimizer(learning_rate=0.001)
train = optimize.minimize(cost)
accr1 = tf.equal(tf.arg_max(pred,1),tf.arg_max(y,1))
accr = tf.reduce_mean(tf.cast(accr1,'float'))
init_op = tf.group(tf.global_variables_initializer(),tf.local_variables_initializer())
with tf.Session() as sess:
sess.run(init_op)
train_epochs = 15
batch_size = 16
avg_cost = 0
total_batch = 10
for epoch in range(train_epochs):
for i in range(total_batch):
example_batch,label_batch = mnist.train.next_batch(batch_size)
feed_train = {x:example_batch,y:label_batch,keepratio:0.7}
sess.run(train,feed_dict=feed_train)
avg_cost += sess.run(cost,feed_dict=feed_train)
avg_cost = avg_cost/total_batch
if (epoch+1) % 2:
feed_train = {x: example_batch, y: label_batch, keepratio: 1.}
# feed_test = {x:test_img,y:test_label}
print('train accr:%f'%sess.run(accr,feed_dict=feed_train))
# print('test accr'%sess.run(accr,feed_dict=feed_test))