0

Ich habe versucht, ein CNN auf dem CIFAR-10-Datensatz für ein paar Tage zu implementieren und meine Testsatzgenauigkeit scheint nicht über die 10% und den Fehler zu gehen einfach herumhängen 69.07733. Ich habe das Modell und einige Tage aber vergeblich gemacht. Ich konnte nicht herausfinden, wo ich falsch liege. Bitte helfen Sie mir, den Fehler im Modell zu erkennen. Hier ist der Code für sie:Neural Network funktioniert nicht gut auf dem CIFAR-10-Datensatz

import os 
import sys 
import pickle 
import tensorflow as tf 
import numpy as np 
from matplotlib import pyplot as plt 

data_root = './cifar-10-batches-py' 
train_data = np.ndarray(shape=(50000,3072), dtype=np.float32) 
train_labels = np.ndarray(shape=(50000), dtype=np.float32) 
num_images = 0 
test_data = np.ndarray(shape=(10000,3072),dtype = np.float32) 
test_labels = np.ndarray(shape=(10000),dtype=np.float32) 
meta_data = {} 

for file in os.listdir(data_root): 
    file_path = os.path.join(data_root,file) 
    with open(file_path,'rb') as f: 
     temp = pickle.load(f,encoding ='bytes') 
     if file == 'batches.meta': 
      for i,j in enumerate(temp[b'label_names']): 
       meta_data[i] = j 
     if 'data_batch_' in file: 
      for i in range(10000): 
       train_data[num_images,:] = temp[b'data'][i] 
       train_labels[num_images] = temp[b'labels'][i] 
       num_images += 1 
     if 'test_batch' in file: 
      for i in range(10000): 
       test_data[i,:] = temp[b'data'][i] 
       test_labels[i] = temp[b'labels'][i] 



'''   
print('meta: \n',meta_data) 
train_data = train_data.reshape(50000,3,32,32).transpose(0,2,3,1) 
print('\ntrain data: \n',train_data.shape,'\nLabels: \n',train_labels[0]) 
print('\ntest data: \n',test_data[0].shape,'\nLabels: \n',train_labels[0])''' 


#accuracy function acc = (no. of correct prediction/total attempts) * 100 
def accuracy(predictions, labels): 
    return (100 * (np.sum(np.argmax(predictions,1)== np.argmax(labels, 1))/predictions.shape[0])) 

#reformat the data 
def reformat(data,labels): 
    data = data.reshape(data.shape[0],3,32,32).transpose(0,2,3,1).astype(np.float32) 
    labels = (np.arange(10) == labels[:,None]).astype(np.float32) 
    return data,labels 


train_data, train_labels = reformat(train_data,train_labels) 
test_data, test_labels = reformat(test_data, test_labels) 
print ('Train ',train_data[0][1]) 

plt.axis("off") 
plt.imshow(train_data[1], interpolation = 'nearest') 
plt.savefig("1.png") 
plt.show() 

''' 
print("Train: \n",train_data.shape,test_data[0],"\nLabels: \n",train_labels.shape,train_labels[:11]) 
print("Test: \n",test_data.shape,test_data[0],"\nLabels: \n",test_labels.shape,test_labels[:11])''' 

image_size = 32 
num_channels = 3 
batch_size = 30 
patch_size = 5 
depth = 64 
num_hidden = 256 
num_labels = 10 

graph = tf.Graph() 

with graph.as_default(): 

    #input data and labels 
    train_input = tf.placeholder(tf.float32,shape=(batch_size,image_size,image_size,num_channels)) 
    train_output = tf.placeholder(tf.float32,shape=(batch_size,num_labels)) 
    test_input = tf.constant(test_data) 

    #layer weights and biases 
    layer_1_weights = tf.Variable(tf.truncated_normal([patch_size,patch_size,num_channels,depth])) 
    layer_1_biases = tf.Variable(tf.zeros([depth])) 

    layer_2_weights = tf.Variable(tf.truncated_normal([patch_size,patch_size,depth,depth])) 
    layer_2_biases = tf.Variable(tf.constant(0.1, shape=[depth])) 

    layer_3_weights = tf.Variable(tf.truncated_normal([64*64, num_hidden])) 
    layer_3_biases = tf.Variable(tf.constant(0.1, shape=[num_hidden])) 

    layer_4_weights = tf.Variable(tf.truncated_normal([num_hidden, num_labels])) 
    layer_4_biases = tf.Variable(tf.constant(0.1, shape=[num_labels])) 

    def convnet(data): 
     conv_1 = tf.nn.conv2d(data, layer_1_weights,[1,1,1,1], padding = 'SAME') 
     hidden_1 = tf.nn.relu(conv_1+layer_1_biases) 
     norm_1 = tf.nn.lrn(hidden_1, 4, bias=1.0, alpha=0.001/9.0, beta=0.75) 
     pool_1 = tf.nn.max_pool(norm_1,[1,2,2,1],[1,2,2,1], padding ='SAME') 
     conv_2 = tf.nn.conv2d(pool_1,layer_2_weights,[1,1,1,1], padding = 'SAME') 
     hidden_2 = tf.nn.relu(conv_2+layer_2_biases) 
     norm_2 = tf.nn.lrn(hidden_2, 4, bias=1.0, alpha=0.001/9.0, beta=0.75) 
     pool_2 = tf.nn.max_pool(norm_2,[1,2,2,1],[1,2,2,1], padding ='SAME') 
     shape = pool_2.get_shape().as_list() 
     hidd2_trans = tf.reshape(pool_2,[shape[0],shape[1]*shape[2]*shape[3]]) 
     hidden_3 = tf.nn.relu(tf.matmul(hidd2_trans,layer_3_weights) + layer_3_biases) 
     return tf.nn.relu(tf.matmul(hidden_3,layer_4_weights) + layer_4_biases) 

    logits = convnet(train_input) 
    loss = tf.reduce_sum(tf.nn.softmax_cross_entropy_with_logits(labels=train_output, logits = logits)) 

    optimizer = tf.train.AdamOptimizer(1e-4).minimize(loss) 

    train_prediction = tf.nn.softmax(logits) 
    test_prediction = tf.nn.softmax(convnet(test_input)) 


num_steps = 100000 


with tf.Session(graph=graph) as session: 
    tf.global_variables_initializer().run() 
    print('Initialized \n') 
    for step in range(num_steps): 
     offset = (step * batch_size) % (train_labels.shape[0] - batch_size) 
     batch = train_data[offset:(offset+batch_size),:,:,:] 
     batch_labels = train_labels[offset:(offset+batch_size),:] 
     feed_dict ={train_input: batch, train_output: batch_labels} 
     _,l,prediction = session.run([optimizer, loss, train_prediction], feed_dict = feed_dict) 
     if (step % 500 == 0): 
      print("Loss at step %d: %f" %(step, l)) 
      print("Accuracy: %f" %(accuracy(prediction, batch_labels))) 
    print("Test accuracy: %f" %(accuracy(session.run(test_prediction), test_labels))) 
+0

Tensorflow hat ein tolles Tutorial dafür. https://github.com/tensorflow/models/tree/master/tutorials/image/cifar10. –

Antwort

0

Auf den ersten Blick würde ich sagen, die Initialisierung der CNN der Schuldige ist. Ein Convnet ist ein Optimierungsalgorithmus in einem stark nichtkonvexen Raum und hängt daher sehr von sorgfältiger Initialisierung ab, damit er nicht auf lokalen Minima oder Sattelpunkten steckenbleibt. Sehen Sie sich xavier initialization an, um zu erfahren, wie Sie das Problem beheben können.

Beispiel Code:

W = tf.get_variable("W", shape=[784, 256], 
      initializer=tf.contrib.layers.xavier_initializer()) 
0

Problem ist das Netzwerk sehr hohe Tiefe aufweist (Anzahl von Filtern = 64 für beide Schichten). Außerdem trainieren Sie das Netzwerk von Grund auf neu. Und Ihr Datensatz von CIFAR10 (50000 Bilder) ist sehr klein. Darüber hinaus ist jedes CIFAR10-Bild nur 32x32x3 groß.

Ein paar Alternativen, was ich Ihnen vorschlagen kann, ist, ein vortrainiertes Modell, d. H. Transferlernen.

Eine andere bessere Alternative ist es, die Anzahl der Filter in jeder Schicht zu reduzieren. Auf diese Weise können Sie das Modell von Grund auf neu trainieren und es wird auch schneller. (Angenommen, Sie haben keine GPU).

Als nächstes verwenden Sie die lokale Antwort Normalisierung. Ich würde vorschlagen, dass Sie diese Schicht entfernen und Normalisierung im Vorverarbeitungsschritt bedeuten.

Als nächstes, wenn Sie glauben, dass das Lernen überhaupt nicht aufgeht, versuchen Sie, die Lernrate etwas zu erhöhen und zu sehen.

schließlich nur eine Operation in Ihrem Code zu reduzieren, können Sie Ihren Tensor neu gestalten und dann in vielen Orten wie dies umsetzen zu tun:

data.reshape(data.shape[0],3,32,32).transpose(0,2,3,1) 

Warum nicht direkt es so etwas neu zu gestalten?

data.reshape(data.shape[0], 32, 32, 3) 

Hoffnung die Antwort hilft Ihnen.

+0

Ich versuchte, die Lernrate zu erhöhen, sogar die Normalisierung entfernt. Da ich Convnets lernen möchte, wollte ich einen von Grund auf neu trainieren und trainiere das Modell auf einer 4 GB Nvidia 940MX. Ich habe tagelang versucht, aber nicht in der Lage zu erkennen, was der Fehler in meinem Modell ist. –

Verwandte Themen