2017-06-12 2 views
2

J'essaie de combiner des couches Conv2D avec des couches LSTM sur des images. Le problème est que les couches Conv2D prennent en entrée un tenseur 4D incluant le nombre de canaux, et mon réseau LSTM a besoin d'un tenseur 3D.Combinaison de couches convolentielles et de couches LSTM avec des séquences de longueur variable

Le problème est que j'utilise le seau, mes entrées n'ont donc pas un nombre prédéfini de timesteps. Je voulais faire quelque chose comme ça:

input_data = Input(shape=[None, nb_features, 1]) 
cnn1 = Conv2D(nb_filters, kernel_size)(input_data) 
cnn2 = Conv2D(nb_filters, kernel_size)(cnn1) 
reshape = Reshape(target_shape=[None, nb_features])(cnn2) 
gru1 = Bidirectional(GRU(rnn_size, return_sequences=True))(reshape) 
gru2 = Bidirectional(GRU(rnn_size, return_sequences=True))(gru1) 
out = TimeDistributed(Dense(nblabels))(gru2) 
output = Activation('softmax')(out) 

Mais le calque Reshape nécessite une forme complètement définie. Y at-il une solution à ce problème?

+0

Qu'est-ce que c'est «nb_features»? Êtes-vous sûr de vouloir un Conv2D (Ex: image 2D) au lieu d'un Conv1D (Ex: un peu de var dans le temps)? --- PS: n'utilise pas "None" dans les formes, et utilise les tuples '(nb_features, 1)' au lieu des listes. –

+0

Dans ce cas, nb_features sera la hauteur de mes images, qui sera constante. Et je suis sûr que je veux un Conv2D sur l'ensemble de l'image et non un ConvolD TimeDistributed. La raison pour laquelle j'utilise None est parce que j'ai besoin de la longueur de ma séquence pour être variable. – Moi4167

+0

Je ne veux pas dire un Conv1D TimeDistributed, je veux dire juste un conv1D. –

Répondre

-1

Ma suggestion est que vous utilisez:

input_data = Input((None, nb_features)) 
cnn1 = Conv1D(nb_filters, kernel_size)(input_data) 
cnn2 = Conv1D(nb_filters, kernel_size)(cnn1) 

gru1 = Bidirectional(GRU(rnn_size, return_sequences=True))(cnn2) 
gru2 = Bidirectional(GRU(rnn_size, return_sequences=True))(gru1) 
out = TimeDistributed(Dense(nblabels))(gru2) 
output = Activation('softmax')(out) 

Ensuite, vous pouvez utiliser un Masking Layer au début (et pad vos données d'entrée avec une valeur factice), ou vous pouvez utiliser de nombreux lots numpy, chaque lot avec une longueur différente, sans masquage ni rembourrage.