TensorFlow BeamSearchDecoder выводит sample_id как (фактический sample_id+1)
- Написал ли я собственный код (вместо использования стандартного сценария, представленного в TensorFlow): Да. На основе учебника по NMT я пишу специальный код для своей задачи.
- Платформа и распространение ОС (например, Linux Ubuntu 16.04): Linux Ubuntu 14.04 LTS
- TensorFlow установлен из (источника или двоичного файла): источник
- Версия TensorFlow (используйте команду ниже): 1.5
- Версия Python: 3.6.3
- Базельская версия (если компилируется из исходного кода): 0.9.0
- Версия GCC/Compiler (если компилируется из исходного кода): 5.4.1
- Версия CUDA/cuDNN:CUDA 8.0, cuDNN 6
- Модель GPU и память: 1080 Ti
- Точная команда для воспроизведения: объясняется в этом посте.
Я пишу код Seq2Seq на основе учебного кода NMT. ( https://github.com/tensorflow/nmt)
Я изменил выходной проектор для декодера, чтобы он был полностью подключенным слоем, а не просто линейным проектором в учебном коде. Определив следующий пользовательский класс Layer:
customlayer.pyhttps://github.com/kami93/ntptest/blob/master/customlayer.py
и затем инициализировал пользовательский слой следующим образом:
with tf.variable_scope("decoder/output_layer"):
output_layer = customlayer.FCLayers(
[256]*2 + [757],
activation = tf.nn.relu,
is_decoder_output=True,
residual=True,
kernel_initializer=initializer,
trainable=True)
затем поместите слой в качестве output_layer BeamSearchDecoder, как это
my_decoder = tf.contrib.seq2seq.BeamSearchDecoder(
cell=cell,
embedding=embedding_decoder,
start_tokens=start_tokens,
end_token=end_token,
initial_state=decoder_initial_state,
beam_width=beam_width,
output_layer=output_layer)
и, наконец, получить вывод sample_id, как это
outputs, final_context_state, _ = tf.contrib.seq2seq.dynamic_decode(
my_decoder,
maximum_iterations=maximum_iterations,
output_time_major=time_major,
swap_memory=True,
scope=decoder_scope)
sample_id = outputs.predicted_ids
Проблема возникает здесь.
Поскольку последнее выходное измерение моего пользовательского слоя - "757", я ожидаю, что sample_id должен быть индексами для argmax id выходного пользовательского слоя, который должен быть между [0,756].
Однако фактический возвращенный sample_id находится между [1 577] (т. Е. Возвращается "мой ожидаемый sample_id + 1").
Ознакомиться с действительным кодом tf.contrib.seq2seq.BeamSearchDecoder можно по адресу https://github.com/tensorflow/tensorflow/blob/r1.5/tensorflow/contrib/seq2seq/python/ops/beam_search_decoder.py... Там является реализацией "_beam_search_step" на линиях между "строкой 510" и "строкой 652",
В строке 545 vacab_size собирается как 757.
vocab_size = logits.shape[-1].value or array_ops.shape(logits)[-1]
В строке 577 индексы с максимальной вероятностью softmax K(ширины луча) определяются среди всех вложенных гипотез "K*757".
next_beam_scores, word_indices = nn_ops.top_k(scores_flat, k=next_beam_size)
В строке 595 фактические индексы вычисляются операцией по модулю.
raw_next_word_ids = math_ops.mod(word_indices, vocab_size,
name="next_beam_word_ids")
next_word_ids = math_ops.to_int32(raw_next_word_ids)
В результате я не вижу никакого смысла в том, что индексы между [1,757] должны возвращаться как sample_id. По крайней мере, из-за операции по модулю 757, которая строго возвращает значение между [0,756], sample_id из 757 никогда не должен возвращаться, по моему мнению. Но я на самом деле понимаю.
Может кто-нибудь подсказать, почему я получаю идентификатор образца [1,757] вместо [0,756]?