Clasificación binaria en TensorFlow, valores grandes inesperados para pérdida y precisión

Estoy tratando de usar una architecture de neural network profunda para clasificar contra un valor de etiqueta binario – -1 y +1. Aquí está mi código para hacerlo en tensorflow .

 import tensorflow as tf import numpy as np from preprocess import create_feature_sets_and_labels train_x,train_y,test_x,test_y = create_feature_sets_and_labels() x = tf.placeholder('float', [None, 5]) y = tf.placeholder('float') n_nodes_hl1 = 500 n_nodes_hl2 = 500 n_nodes_hl3 = 500 n_classes = 1 batch_size = 100 def neural_network_model(data): hidden_1_layer = {'weights':tf.Variable(tf.random_normal([5, n_nodes_hl1])), 'biases':tf.Variable(tf.random_normal([n_nodes_hl1]))} hidden_2_layer = {'weights':tf.Variable(tf.random_normal([n_nodes_hl1, n_nodes_hl2])), 'biases':tf.Variable(tf.random_normal([n_nodes_hl2]))} hidden_3_layer = {'weights':tf.Variable(tf.random_normal([n_nodes_hl2, n_nodes_hl3])), 'biases':tf.Variable(tf.random_normal([n_nodes_hl3]))} output_layer = {'weights':tf.Variable(tf.random_normal([n_nodes_hl3, n_classes])), 'biases':tf.Variable(tf.random_normal([n_classes]))} l1 = tf.add(tf.matmul(data, hidden_1_layer['weights']), hidden_1_layer['biases']) l1 = tf.nn.relu(l1) l2 = tf.add(tf.matmul(l1, hidden_2_layer['weights']), hidden_2_layer['biases']) l2 = tf.nn.relu(l2) l3 = tf.add(tf.matmul(l2, hidden_3_layer['weights']), hidden_3_layer['biases']) l3 = tf.nn.relu(l3) output = tf.transpose(tf.add(tf.matmul(l3, output_layer['weights']), output_layer['biases'])) return output def train_neural_network(x): prediction = neural_network_model(x) cost = tf.reduce_mean(tf.nn.sigmoid_cross_entropy_with_logits(prediction, y)) optimizer = tf.train.AdamOptimizer().minimize(cost) hm_epochs = 10 with tf.Session() as sess: sess.run(tf.initialize_all_variables()) for epoch in range(hm_epochs): epoch_loss = 0 i = 0 while i < len(train_x): start = i end = i + batch_size batch_x = np.array(train_x[start:end]) batch_y = np.array(train_y[start:end]) _, c = sess.run([optimizer, cost], feed_dict={x: batch_x, y: batch_y}) epoch_loss += c i+=batch_size print('Epoch', epoch, 'completed out of', hm_epochs, 'loss:', epoch_loss) # correct = tf.equal(tf.argmax(prediction, 1), tf.argmax(y, 1)) # accuracy = tf.reduce_mean(tf.cast(correct, 'float')) print (test_x.shape) accuracy = tf.nn.l2_loss(prediction-y,name="squared_error_test_cost")/test_x.shape[0] print('Accuracy:', accuracy.eval({x: test_x, y: test_y})) train_neural_network(x) 

Esta es la salida que obtengo cuando ejecuto esto:

 ('Epoch', 0, 'completed out of', 10, 'loss:', -8400.2424869537354) ('Epoch', 1, 'completed out of', 10, 'loss:', -78980.956665039062) ('Epoch', 2, 'completed out of', 10, 'loss:', -152401.86713409424) ('Epoch', 3, 'completed out of', 10, 'loss:', -184913.46441650391) ('Epoch', 4, 'completed out of', 10, 'loss:', -165563.44775390625) ('Epoch', 5, 'completed out of', 10, 'loss:', -360394.44857788086) ('Epoch', 6, 'completed out of', 10, 'loss:', -475697.51550292969) ('Epoch', 7, 'completed out of', 10, 'loss:', -588638.92993164062) ('Epoch', 8, 'completed out of', 10, 'loss:', -745006.15966796875) ('Epoch', 9, 'completed out of', 10, 'loss:', -900172.41955566406) (805, 5) ('Accuracy:', 5.8077128e+09) 

No entiendo si los valores que estoy obteniendo son correctos ya que hay una escasez real de ejemplos de clasificación binaria que no son MNIST. La precisión no se parece en nada a lo que esperaba. Esperaba un porcentaje en lugar de ese gran valor.

También estoy algo inseguro de la teoría detrás del aprendizaje automático, por lo que no puedo decir lo correcto de mi enfoque utilizando tensorflow.

¿Puede alguien decirme si mi enfoque hacia la clasificación binaria es correcto? También es correcta la parte de mi código?

De esto:

un valor de etiqueta binario – -1 y +1

. . . Estoy asumiendo que tus valores en train_y y test_y son en realidad -1.0 y +1.0

Esto no va a funcionar muy bien con la función de pérdida elegida sigmoid_cross_entropy_with_logits , que supone 0.0 y +1.0. Los valores negativos de y están causando caos! Sin embargo, la elección de la función de pérdida es buena para la clasificación binaria. Sugiero cambiar los valores de y a 0 y 1.

Además, técnicamente la salida de su red no es la predicción final. La función de pérdida sigmoid_cross_entropy_with_logits está diseñada para trabajar con una red con la función de transferencia sigmoide en la capa de salida, aunque está correcto que la función de pérdida se aplique antes de que se haga esto. Entonces tu código de entrenamiento parece correcto

tf.transpose embargo, no estoy 100% seguro de la tf.transpose qué sucede si eliminas eso, personalmente.

 output = tf.add(tf.matmul(l3, output_layer['weights']), output_layer['biases']) 

De cualquier manera, esta es la salida “logit”, pero no su predicción. El valor de la output puede ser alto para predicciones muy confiables, lo que probablemente explica sus valores muy altos más adelante debido a que falta la función sigmoide. Entonces agregue un tensor de predicción (esto representa la probabilidad / confianza de que el ejemplo está en la clase positiva):

 prediction = tf.sigmoid(output) 

Puedes usar eso para calcular la precisión. Su cálculo de precisión no debe basarse en el error L2, sino en la sum de los valores correctos, más cerca del código que comentó (que parece ser de una clasificación multiclase). Para una comparación con verdadero / falso para la clasificación binaria, debe umbralizar las predicciones y comparar con las tags verdaderas. Algo como esto:

  predicted_class = tf.greater(prediction,0.5) correct = tf.equal(predicted_class, tf.equal(y,1.0)) accuracy = tf.reduce_mean( tf.cast(correct, 'float') ) 

El valor de precisión debe estar entre 0.0 y 1.0. Si quieres como porcentaje, simplemente multiplica por 100 por supuesto.