0

Я реализовал двунаправленный RNN в TensorFlow, используя BasicLSTMCell и . Я вычисляю потери с использованием seq2seq.sequence_loss_by_example после конкатенации выходов, которые я получаю. Мое приложение - следующий предиктор символов.Получение чрезвычайно низких потерь в двунаправленном RNN?

Я получаю чрезвычайно низкийcost, (~ 50 раз меньше, чем однонаправленный RNN). Я подозреваю, что совершил ошибку на этапе seq2seq.sequence_loss_by_example.

Вот моя модель -

# Model begins 
cell_fn = rnn_cell.BasicLSTMCell 
cell = fw_cell = cell_fn(args.rnn_size, state_is_tuple=True) 
cell2 = bw_cell = cell_fn(args.rnn_size, state_is_tuple=True) 

input_data = tf.placeholder(tf.int32, [args.batch_size, args.seq_length]) 
targets = tf.placeholder(tf.int32, [args.batch_size, args.seq_length]) 
initial_state = fw_cell.zero_state(args.batch_size, tf.float32) 
initial_state2 = bw_cell.zero_state(args.batch_size, tf.float32) 

with tf.variable_scope('rnnlm'): 
    softmax_w = tf.get_variable("softmax_w", [2*args.rnn_size, args.vocab_size]) 
    softmax_b = tf.get_variable("softmax_b", [args.vocab_size]) 
    with tf.device("/cpu:0"): 
    embedding = tf.get_variable("embedding", [args.vocab_size, args.rnn_size]) 
    input_embeddings = tf.nn.embedding_lookup(embedding, input_data) 
    inputs = tf.unpack(input_embeddings, axis=1) 

outputs, last_state, last_state2 = rnn.bidirectional_rnn(fw_cell, 
                 bw_cell, 
                 inputs, 
                 initial_state_fw=initial_state, 
                 initial_state_bw=initial_state2, 
                 dtype=tf.float32) 
output = tf.reshape(tf.concat(1, outputs), [-1, 2*args.rnn_size]) 
logits = tf.matmul(output, softmax_w) + softmax_b 

probs = tf.nn.softmax(logits) 
loss = seq2seq.sequence_loss_by_example([logits], 
     [tf.reshape(targets, [-1])], 
     [tf.ones([args.batch_size * args.seq_length])], 
     args.vocab_size) 
cost = tf.reduce_sum(loss)/args.batch_size/args.seq_length 
lr = tf.Variable(0.0, trainable=False) 
tvars = tf.trainable_variables() 
grads, _ = tf.clip_by_global_norm(tf.gradients(cost, tvars), 
     args.grad_clip) 
optimizer = tf.train.AdamOptimizer(lr) 
train_op = optimizer.apply_gradients(zip(grads, tvars)) 
+0

Буду рад предоставить дополнительную информацию, если необходимо – martianwars

ответ

1

Я думаю, что нет никакой ошибки в коде.

Проблема заключается в целевой функции с моделью Bi-RNN в вашем приложении (следующий предиктор символов).

Однонаправленный РНН (например, ptb_word_lm или char-rnn-tensorflow), это действительно модель, используемая для предсказания, например, если raw_text является 1,3,5,2,4,8,9,0, то ваш inputs и target будет:

inputs: 1,3,5,2,4,8,9 
target: 3,5,2,4,8,9,0 

и предсказание (1)->3, (1,3)->5 ..., (1,3,5,2,4,8,9)->0

Но в Bi-RNN, первое предсказание действительно не просто (1)->3, потому что output[0] в вашем коде соответствует обратная информация raw_text с использованием bw_cell (также не (1,3)->5, ..., (1,3,5,2,4,8,9)->0). Аналогичный пример: я говорю вам, что цветок - это роза, и чем я позволяю вам предсказать, что такое цветок? Я думаю, что вы можете дать мне правильный ответ очень легко, и это также является причиной того, что вы получаете крайне низкую loss в вашей модели Bi-RNN для приложения.

На самом деле, я думаю, что Bi-RNN (или Bi-LSTM) не является подходящей моделью для применения следующего предиктора символов. Bi-RNN нуждается в полной последовательности, когда он работает, вы обнаружите, что не можете использовать эту модель легко, если хотите предсказать следующий символ.

+0

Что было бы хорошим способом рассчитать потерю? Должен ли я использовать ошибку RMS? – martianwars

Смежные вопросы