我使用TensorFlow和Python3构建了一个CNN(卷积神经网络)模型来训练和预测MNIST手写数字数据库。
from tensorflow.examples.tutorials.mnist import input_data
我用MNIST训练数据库训练了我的CNN模型,并用MNIST测试数据库进行预测。我的模型准确率超过了95%,结果还不错。
import tensorflow as tfimport osfrom tensorflow.examples.tutorials.mnist import input_datatf.logging.set_verbosity(tf.logging.ERROR)def compute_accuracy(v_xs, v_ys): global prediction y_pre = sess.run(prediction, feed_dict={xs: v_xs, keep_prob: 1}) correct_prediction = tf.equal(tf.argmax(y_pre, 1), tf.argmax(v_ys, 1)) accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32)) result = sess.run(accuracy, feed_dict={xs: v_xs, ys: v_ys, keep_prob: 1}) return resultdef weight_variable(shape): initial = tf.truncated_normal(shape, stddev=0.1) return tf.Variable(initial)def bias_variable(shape): initial = tf.constant(0.1, shape=shape) return tf.Variable(initial)def conv2d(x, W): return tf.nn.conv2d(input=x, filter=W, strides=[1, 1, 1, 1], padding='SAME')def max_pool_2x2(x): return tf.nn.max_pool(x, ksize=[1, 2, 2, 1], strides=[1, 2, 2, 1], padding='SAME')IMAGE_WIDTH = 28IMAGE_HEIGHT = 28CHANNEL_COUNT = 1CONV1_FEATURE_MAP_COUNT = 32CONV1_FILTER_HEIGHT = 5CONV1_FILTER_WEIGHT = 5CONV2_FILTER_HEIGHT = 5CONV2_FILTER_WEIGHT = 5CONV2_FEATURE_MAP_COUNT = 64FULL_CONNECTED_OUTPUT_SIZE = 1024OUTPUT_TYPE_COUNT = 10mnist = input_data.read_data_sets('MNIST_data', one_hot=True)pb_file_dir = "{path}{sep}pb_modelsaved_model".format(path=os.getcwd(), sep=os.path.sep)ckpt_file_dir = "{path}{sep}ckpt_model{sep}model.ckpt".format(path=os.getcwd(), sep=os.path.sep)with tf.name_scope('input'): xs = tf.placeholder(tf.float32, [None, IMAGE_WIDTH * IMAGE_HEIGHT], name="images") / 255. # 28x28 ys = tf.placeholder(tf.float32, [None, 10], name="labels") keep_prob = tf.placeholder(tf.float32, name="keep_prob")x_image = tf.reshape(xs, [-1, IMAGE_HEIGHT, IMAGE_WIDTH, CHANNEL_COUNT])with tf.name_scope("conv_layer1"): with tf.name_scope('weights'): W_conv1 = weight_variable([CONV1_FILTER_HEIGHT, CONV1_FILTER_WEIGHT, CHANNEL_COUNT, CONV1_FEATURE_MAP_COUNT]) with tf.name_scope('biases'): b_conv1 = bias_variable([CONV1_FEATURE_MAP_COUNT]) with tf.name_scope('conv'): h_conv1 = tf.nn.relu(conv2d(x_image, W_conv1) + b_conv1) with tf.name_scope('pool'): h_pool1 = max_pool_2x2(h_conv1)with tf.name_scope("conv_layer2"): with tf.name_scope('weights'): W_conv2 = weight_variable( [CONV2_FILTER_HEIGHT, CONV2_FILTER_WEIGHT, CONV1_FEATURE_MAP_COUNT, CONV2_FEATURE_MAP_COUNT]) with tf.name_scope('biases'): b_conv2 = bias_variable([CONV2_FEATURE_MAP_COUNT]) with tf.name_scope('conv'): h_conv2 = tf.nn.relu(conv2d(h_pool1, W_conv2) + b_conv2) with tf.name_scope('pool'): h_pool2 = max_pool_2x2(h_conv2)with tf.name_scope("fc_layer1"): with tf.name_scope('weights'): W_fc1 = weight_variable([7 * 7 * 64, FULL_CONNECTED_OUTPUT_SIZE]) with tf.name_scope('biases'): b_fc1 = bias_variable([FULL_CONNECTED_OUTPUT_SIZE]) with tf.name_scope('output'): h_pool2_flat = tf.reshape(h_pool2, [-1, 7 * 7 * 64]) h_fc1 = tf.nn.relu(tf.matmul(h_pool2_flat, W_fc1) + b_fc1)with tf.name_scope("fc_layer2"): with tf.name_scope('weights'): W_fc2 = weight_variable([FULL_CONNECTED_OUTPUT_SIZE, OUTPUT_TYPE_COUNT]) with tf.name_scope('biases'): b_fc2 = bias_variable([OUTPUT_TYPE_COUNT]) with tf.name_scope('output'): h_fc1_drop = tf.nn.dropout(h_fc1, keep_prob, name="drop") prediction = tf.nn.softmax(tf.matmul(h_fc1_drop, W_fc2) + b_fc2, name="prediction")with tf.name_scope('loss'): cross_entropy = tf.reduce_mean( -tf.reduce_sum(ys * tf.log(prediction), reduction_indices=[1]), name="loss")with tf.name_scope('train'): train_step = tf.train.AdamOptimizer(1e-4).minimize(cross_entropy, name="train_step")saver = tf.train.Saver()with tf.Session() as sess: sess.run(tf.global_variables_initializer()) for i in range(1000): batch_xs, batch_ys = mnist.train.next_batch(100) sess.run(train_step, feed_dict={xs: batch_xs, ys: batch_ys, keep_prob: 0.5}) if i % 50 == 0: accuracy = compute_accuracy(mnist.test.images[:1000], mnist.test.labels[:1000]) save_path = saver.save(sess, ckpt_file_dir)
然而,当我尝试保存我的模型并恢复模型来预测MNIST测试数据库时,我的模型准确率只有10%!
import tensorflow as tfimport osfrom tensorflow.examples.tutorials.mnist import input_datatf.logging.set_verbosity(tf.logging.ERROR)mnist = input_data.read_data_sets('MNIST_data', one_hot=True)ckpt_file_dir = "{path}{sep}ckpt_model{sep}model.ckpt".format(path=os.getcwd(), sep=os.path.sep)def compute_accuracy(v_xs, v_ys): global prediction y_pre = sess.run(prediction, feed_dict={xs: v_xs, keep_prob: 1}) correct_prediction = tf.equal(tf.argmax(y_pre, 1), tf.argmax(v_ys, 1)) accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32)) result = sess.run(accuracy, feed_dict={xs: v_xs, ys: v_ys, keep_prob: 1}) return resulttf.reset_default_graph()with tf.Session() as sess: saver = tf.train.import_meta_graph(ckpt_file_dir + ".meta") saver.restore(sess, ckpt_file_dir) xs = sess.graph.get_tensor_by_name('input/images:0') ys = sess.graph.get_tensor_by_name('input/labels:0') keep_prob = sess.graph.get_tensor_by_name('input/keep_prob:0') prediction = sess.graph.get_tensor_by_name('fc_layer2/output/prediction:0') cross_entropy = sess.graph.get_tensor_by_name('loss/loss:0') print(compute_accuracy(mnist.test.images[:1000], mnist.test.labels[:1000]))
这对我来说非常困难,因为我对TensorFlow还不熟悉。我尝试打印我保存的模型中的所有变量,发现它们与训练后的模型是一样的。
我还尝试用“pb”文件保存我的模型,结果准确率仍然是10%!
我被这个问题困扰,希望你能帮我解决这个问题!谢谢你!
我尝试打印模型中所有权重的名称:
W_conv1 conv_layer1/weights/Variable:0W_conv2 conv_layer2/weights/Variable:0W_fc1 fc_layer1/weights/Variable:0W_fc2 fc_layer2/weights/Variable:0
我尝试打印标签值和预测值的结果:
回答:
我找到了代码的问题所在。
我将这行代码:
xs = tf.placeholder(tf.float32, [None, IMAGE_WIDTH * IMAGE_HEIGHT], name="images") / 255
改为:
xs = tf.placeholder(tf.float32, [None, IMAGE_WIDTH * IMAGE_HEIGHT], name="images")
这样就没问题了!