web-dev-qa-db-fra.com

ValueError: tentative de partage de la variable rnn / multi_rnn_cell / cell_0 / basic_lstm_cell / kernel

C'est le code:

X = tf.placeholder(tf.float32, [batch_size, seq_len_1, 1], name='X')
labels = tf.placeholder(tf.float32, [None, alpha_size], name='labels')

rnn_cell = tf.contrib.rnn.BasicLSTMCell(512)
m_rnn_cell = tf.contrib.rnn.MultiRNNCell([rnn_cell] * 3, state_is_Tuple=True)
pre_prediction, state = tf.nn.dynamic_rnn(m_rnn_cell, X, dtype=tf.float32)

C'est une erreur complète:

ValueError: Essayer de partager la variable rnn/multi_rnn_cell/cell_0/basic_lstm_cell/kernel, mais la forme spécifiée (1024, 2048) et la forme trouvée (513, 2048).

J'utilise une version GPU de tensorflow.

19

J'ai rencontré un problème similaire lors de la mise à niveau vers la version 1.2 (tensorflow-gpu). À la place d'utiliser [rnn_cell]*3, J'ai créé 3 rnn_cells (stacked_rnn) par une boucle (pour qu'ils ne partagent pas de variables) et alimenté MultiRNNCell avec stacked_rnn et le problème disparaît. Je ne suis pas sûr que ce soit la bonne façon de procéder.

stacked_rnn = []
for iiLyr in range(3):
    stacked_rnn.append(tf.nn.rnn_cell.LSTMCell(num_units=512, state_is_Tuple=True))
MultiLyr_cell = tf.nn.rnn_cell.MultiRNNCell(cells=stacked_rnn, state_is_Tuple=True)
30
Maosi Chen

Un tutoriel officiel TensorFlow recommande cette façon de définir plusieurs réseaux LSTM:

def lstm_cell():
  return tf.contrib.rnn.BasicLSTMCell(lstm_size)
stacked_lstm = tf.contrib.rnn.MultiRNNCell(
    [lstm_cell() for _ in range(number_of_layers)])

Vous pouvez le trouver ici: https://www.tensorflow.org/tutorials/recurrent

En fait, c'est presque la même approche que Wasi Ahmad et Maosi Chen ont suggéré ci-dessus mais peut-être sous une forme un peu plus élégante.

14
Dmitry Malov

Je suppose que c'est parce que vos cellules RNN sur chacune de vos 3 couches partagent la même forme d'entrée et de sortie.

Sur la couche 1, la dimension d'entrée est 513 = 1 (votre dimension x) + 512 (dimension de la couche masquée) pour chaque horodatage par lot.

Sur les couches 2 et 3, la dimension d'entrée est 1024 = 512 (sortie de la couche précédente) + 512 (sortie de l'horodatage précédent).

La façon dont vous empilez votre MultiRNNCell implique probablement que 3 cellules partagent la même forme d'entrée et de sortie.

J'empile MultiRNNCell en déclarant deux types de cellules distincts afin de les empêcher de partager la forme d'entrée

rnn_cell1 = tf.contrib.rnn.BasicLSTMCell(512)
run_cell2 = tf.contrib.rnn.BasicLSTMCell(512)
stack_rnn = [rnn_cell1]
for i in range(1, 3):
    stack_rnn.append(rnn_cell2)
m_rnn_cell = tf.contrib.rnn.MultiRNNCell(stack_rnn, state_is_Tuple = True)

Ensuite, je suis capable de former mes données sans ce bug. Je ne sais pas si ma supposition est correcte, mais cela fonctionne pour moi. J'espère que ça marche pour toi.

5
Jack Lv