Python 具有自定义数据集的Tensorflow卷积神经网络不学习

Python 具有自定义数据集的Tensorflow卷积神经网络不学习,python,machine-learning,computer-vision,tensorflow,deep-learning,Python,Machine Learning,Computer Vision,Tensorflow,Deep Learning,我正在尝试为自定义数据集制作一个卷积神经网络。分类器只有两个类。我能够正确地阅读输入图像,并为它们分配了两个相应类的批次标签。代码执行时没有错误,但输出异常。 由于某些原因,准确率始终为50% image=inputs() image_batch=tf.train.batch([image],batch_size=150) label_batch_pos=tf.train.batch([tf.constant([0,1])],batch_size=75) # label_batch for f

我正在尝试为自定义数据集制作一个卷积神经网络。分类器只有两个类。我能够正确地阅读输入图像,并为它们分配了两个相应类的批次标签。代码执行时没有错误,但输出异常。 由于某些原因,准确率始终为50%

image=inputs()

image_batch=tf.train.batch([image],batch_size=150)
label_batch_pos=tf.train.batch([tf.constant([0,1])],batch_size=75) # label_batch for first class
label_batch_neg=tf.train.batch([tf.constant([1,0])],batch_size=75) # label_batch for second class
label_batch=tf.concat(0,[label_batch_pos,label_batch_neg])

W_conv1 = weight_variable([5, 5, 3, 32])
b_conv1 = bias_variable([32])

image_4d = tf.reshape(image, [-1,32,32,3])

h_conv1 = tf.nn.relu(conv2d(image_4d, W_conv1) + b_conv1)
h_pool1 = max_pool_2x2(h_conv1)

W_conv2 = weight_variable([5, 5, 32, 64])
b_conv2 = bias_variable([64])

h_conv2 = tf.nn.relu(conv2d(h_pool1, W_conv2) + b_conv2)
h_pool2 = max_pool_2x2(h_conv2)

W_fc1 = weight_variable([8 * 8 * 64, 1024])
b_fc1 = bias_variable([1024])

h_pool2_flat = tf.reshape(h_pool2, [-1, 8*8*64])
h_fc1 = tf.nn.relu(tf.matmul(h_pool2_flat, W_fc1) + b_fc1)
h_fc1_drop = tf.nn.dropout(h_fc1, 0.5)

W_fc2 = weight_variable([1024, 2])
b_fc2 = bias_variable([2])

y_conv=tf.nn.softmax(tf.matmul(h_fc1_drop, W_fc2) + b_fc2)
cross_entropy = -tf.reduce_sum(tf.cast(label_batch,tf.float32)*tf.log(y_conv+1e-9))
train_step = tf.train.AdamOptimizer(1e-4).minimize(cross_entropy)

init = tf.initialize_all_variables()
sess = tf.Session()
sess.run(init)


tf.train.start_queue_runners(sess=sess)
correct_prediction=tf.equal(tf.argmax(y_conv,1), tf.argmax(label_batch,1))
accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32))

for i in range(100):
 train_step.run(session=sess)
 print(sess.run(accuracy))

print(sess.run(correct_prediction))
当我打印
correct\u prediction
tensor时,无论发生什么,我都会得到以下输出

[ True  True  True  True  True  True  True  True  True  True  True  True
  True  True  True  True  True  True  True  True  True  True  True  True
  True  True  True  True  True  True  True  True  True  True  True  True
  True  True  True  True  True  True  True  True  True  True  True  True
  True  True  True  True  True  True  True  True  True  True  True  True
  True  True  True  True  True  True  True  True  True  True  True  True
  True  True  True False False False False False False False False False
 False False False False False False False False False False False False
 False False False False False False False False False False False False
 False False False False False False False False False False False False
 False False False False False False False False False False False False
 False False False False False False False False False False False False
 False False False False False False]
精度始终为0.5,就好像根本没有更新权重一样。当我在每个训练步骤后打印权重时,它们保持不变。我想我有一些编码错误。难道网络一次又一次地在同一张图片上训练?但即便如此,权重也必须更新。我有150个训练例子,每个班有75个。 有人能给我指一下正确的方向吗

编辑: 这就是我初始化权重的方式

def weight_variable(shape,name):
  initial = tf.truncated_normal(shape, stddev=0.5)
  return tf.Variable(initial,name=name)

def bias_variable(shape,name):
  initial = tf.constant(1.0, shape=shape)
  return tf.Variable(initial,name=name)

您的网络存在一些设计缺陷。由于数学问题,自己计算交叉熵并在输出层上应用softmax不是一个好主意。如果你对数学感兴趣,我可以加上这个,如果不坚持Tensorflow的解释和方法:

您是否已经尝试过许多不同的配置?根据图像的复杂程度,增加或减少内核大小和功能映射的数量可能是一个好主意。通常,如果您的图像相对同质,则会添加许多非常相似的信息,因此,如果您有许多特征贴图,网络将更难收敛。既然你只有两个输出神经元,我想图像不是很复杂吧

接下来是你的辍学。您总是使用0.5的辍学率,但通常,对于测试/验证(如精度预测),您不使用辍学率。在大多数情况下,您仅将其用于培训。您可以创建一个占位符,指定您的辍学率,并将此
sess.run

以下是我自己的一些例子:

h_fc_drop = tf.nn.dropout(h_fc, keep_prob)

(...)

accu, top1, top3, top5 = sess.run([accuracy, te_top1, te_top3, te_top5],
                            feed_dict={
                                x: teX[i: i + batch_size],
                                y: teY[i: i + batch_size]
                                keep_prob: 1.0
                            }
                         )
这允许Tensorflow计算我的
准确度
topX
错误率方程,同时输入测试数据输入
teX
和输出的真实标签
teY
,辍学的保留概率
keep_prob
为1.0

尽管如此,权重的初始化在深度神经网络中还是非常重要的。即使您的设计足以解决此类问题(这也必须进行调查),如果权重未正确初始化,您的网络也可能拒绝学习、发散或收敛到0。您没有向初始化中添加详细信息,因此可能需要查找Xavier初始化。这是Xavier初始化的一个简单开始


最后,我可以鼓励您绘制一些权重、特征图、随时间变化的输出等,以了解您的网络正在做什么。通常这很有帮助。

谢谢!首先,是的,我想知道不使用softmax层背后的数学原理。其次,我没有使用feed_dict,因为我的输入只有一个批,它们是张量,而不是numpy数组。第三,是的,我尝试了很多配置,但没有缓解。无论发生什么,网络都拒绝学习。我认为这是一个编码缺陷。第四,我试过了,也没有辍学,但没有让我松一口气。第五,我也初始化了权重,这样就不会有死亡的神经元。我编辑了这个问题,让你更好地理解这个问题。再次感谢!在哪里,更重要的是如何初始化权重?我已经编辑了这个问题,显示了权重初始化。你的初始化太大了。你的照片有多大?对于1000个神经元,stddev为