keras: Undefined output shape in Conv2DTranspose

If we use keras with tensorflow, the output shape of a Conv2DTranspose is undefined even if the input shape is fixed. This problem doesn’t happen with Conv2D . This is probably due to a bug in the implementation of Conv2DTranspose.

import tensorflow as tf

config = tf.ConfigProto()
config.gpu_options.allow_growth=True
sess = tf.Session(config=config)

from keras.layers.convolutional import Conv2DTranspose , Conv2D

layer1 = Conv2DTranspose( 8  , (4 , 4) , strides=(1, 1)  , data_format='channels_first'  , input_shape=(3,64,64) )
layer2 = Conv2D( 8 , (4, 4) , strides=(1, 1), input_shape=(3, 64, 64) , data_format='channels_first'  )

BATCH_SIZE = 32
x = tf.placeholder(tf.float32, shape=( BATCH_SIZE , 3, 64 , 64 ))
          
o1 = layer1( x )
o2 = layer2( x )


print o1.get_shape() # Prints (?, 8, ?, ?) , why???
print o2.get_shape() # Prints (32, 8, 61, 61) , which is correct 

About this issue

  • Original URL
  • State: closed
  • Created 7 years ago
  • Reactions: 5
  • Comments: 21 (2 by maintainers)

Most upvoted comments

I can check the output shape with _keras_shape property of the layer.

A nasty workaround is to explicitly mention the output shape.
<your_tensor>.set_shape(<output_shape>)

Changing the imports to the Keras version included in Tensorflow also fixed the problem:

from tensorflow.python import keras
from tensorflow.python.keras.layers import Input, Conv2D, Conv2DTranspose
from tensorflow.python.keras import backend as K

assert K.image_data_format() == 'channels_last'

inp = Input(shape=(((32, 32, 3))))
out_1 = Conv2D(8, (3, 3), strides=(1, 1), padding='same')(inp)
out_2 = Conv2DTranspose(8, (3, 3), strides=(1, 1), padding='same')(inp)

print(out_1.shape)
print(out_2.shape)
(?, 32, 32, 8)
(?, 32, 32, 8)

@wt-huang Is this really resolved? It seems like the solution above is “abandon Keras and use tf.keras”, which isn’t ideal.

My latest pull request fixes this issue: #13778

@wt-huang This isn’t solved! Keras from TF and vanilla keras is not compatible. A project should use either tf.keras or just keras and not both. Changing the whole project to use tf.keras is a huge job.

I too encoutered this bug.

The following code

from keras.models import Model
from keras.layers import Input, Conv2D, Conv2DTranspose
from keras import backend as K

assert K.image_data_format() == 'channels_last'

inp = Input(shape=(((32, 32, 3))))
out_1 = Conv2D(8, (3, 3), strides=(1, 1), padding='same')(inp)
out_2 = Conv2DTranspose(8, (3, 3), strides=(1, 1), padding='same')(inp)

print(out_1.shape)
print(out_2.shape)

produces this output (Keras Version 2.0.8, TensorFlow 1.3.0)

(?, 32, 32, 8)
(?, ?, ?, 8)

To me it looks like it is caused by this TensorFlow issue.

I suppose that’s that, then. Still pretty annoying since, a) TF 2.0 is still in beta, and b) tf.keras is not a drop-in replacement, as evidenced by the week or so of work I had to put in switching over to get around this bug.

(The latter point may now be true with the 2.3.0 update, but I think that also points towards the high volatility in machine learning libraries.)

I encountered the same issue! I had to use the following to determine the output shape: shape_o1 = layer1.compute_output_shape(input_shape)