Search code examples
pythontensorflowinputdataformattensorflow-probability

TypeError: Failed to convert object of type <class 'list'> to Tensor. Contents: [None, 16, 16384, 128]. Consider casting elements to a supported type


I get the following error when fitting the model: TypeError: Failed to convert object of type <class 'list'> to Tensor. Contents: [None, 16, 16384, 128]. Consider casting elements to a supported type.

This is where I define the input shape in the model:

from tensorflow.keras.layers import Input

def model(input_shape=(4, 128, 128, 128),n_base_filters=16, depth=5, dropout_rate=0.3,
                      n_segmentation_levels=3, n_labels=4, optimizer=Adam, initial_learning_rate=5e-4,
                      loss_function=bin_crossentropy, activation_name="sigmoid",metrics=dice_coefficient):

    inputs = Input(input_shape)
    ......

Traceback:

---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
/usr/local/lib/python3.7/dist-packages/tensorflow/python/framework/tensor_util.py in make_tensor_proto(values, dtype, shape, verify_shape, allow_broadcast)
    548     try:
--> 549       str_values = [compat.as_bytes(x) for x in proto_values]
    550     except TypeError:

24 frames
/usr/local/lib/python3.7/dist-packages/tensorflow/python/framework/tensor_util.py in <listcomp>(.0)
    548     try:
--> 549       str_values = [compat.as_bytes(x) for x in proto_values]
    550     except TypeError:

/usr/local/lib/python3.7/dist-packages/tensorflow/python/util/compat.py in as_bytes(bytes_or_text, encoding)
     86     raise TypeError('Expected binary or unicode string, got %r' %
---> 87                     (bytes_or_text,))
     88 

TypeError: Expected binary or unicode string, got None

During handling of the above exception, another exception occurred:

TypeError                                 Traceback (most recent call last)
<ipython-input-56-c79d6965b744> in <module>()
      1 model=model(input_shape=(4, 128, 128, 128),n_base_filters=16, depth=5, dropout_rate=0.3,
      2                       n_segmentation_levels=3, n_labels=4, optimizer=Adam, initial_learning_rate=5e-4,
----> 3                       loss_function=weighted_dice_coefficient_loss, activation_name="sigmoid",metrics=dice_coefficient)
      4 
      5 print(len(model.layers))

<ipython-input-55-051eee07240c> in model(input_shape, n_base_filters, depth, dropout_rate, n_segmentation_levels, n_labels, optimizer, initial_learning_rate, loss_function, activation_name, metrics)
     48 
     49         if current_layer is inputs:
---> 50             in_conv = create_convolution_block_flip(current_layer, n_level_filters)
     51         else:
     52             in_conv = create_convolution_block_flip(current_layer,n_level_filters, strides=(2, 2, 2))

<ipython-input-42-e2034c0ac3eb> in create_convolution_block_flip(input_layer, n_filters, num_train_examples, batch_normalization, kernel, activation, padding, strides, instance_normalization)
      7                             tf.cast(num_train_examples, dtype=tf.float32)) 
      8 
----> 9     layer = tfp.layers.Convolution3DFlipout(n_filters, kernel, padding=padding, strides=strides, data_format="channels_first",kernel_divergence_fn=kl_diverge_func)(input_layer)
     10 
     11 

/usr/local/lib/python3.7/dist-packages/tensorflow/python/keras/engine/base_layer.py in __call__(self, *args, **kwargs)
    968     if _in_functional_construction_mode(self, inputs, args, kwargs, input_list):
    969       return self._functional_construction_call(inputs, args, kwargs,
--> 970                                                 input_list)
    971 
    972     # Maintains info about the `Layer.call` stack.

/usr/local/lib/python3.7/dist-packages/tensorflow/python/keras/engine/base_layer.py in _functional_construction_call(self, inputs, args, kwargs, input_list)
   1106       # Check input assumptions set after layer building, e.g. input shape.
   1107       outputs = self._keras_tensor_symbolic_call(
-> 1108           inputs, input_masks, args, kwargs)
   1109 
   1110       if outputs is None:

/usr/local/lib/python3.7/dist-packages/tensorflow/python/keras/engine/base_layer.py in _keras_tensor_symbolic_call(self, inputs, input_masks, args, kwargs)
    838       return nest.map_structure(keras_tensor.KerasTensor, output_signature)
    839     else:
--> 840       return self._infer_output_signature(inputs, args, kwargs, input_masks)
    841 
    842   def _infer_output_signature(self, inputs, args, kwargs, input_masks):

/usr/local/lib/python3.7/dist-packages/tensorflow/python/keras/engine/base_layer.py in _infer_output_signature(self, inputs, args, kwargs, input_masks)
    878           self._maybe_build(inputs)
    879           inputs = self._maybe_cast_inputs(inputs)
--> 880           outputs = call_fn(inputs, *args, **kwargs)
    881 
    882         self._handle_activity_regularization(inputs, outputs)

/usr/local/lib/python3.7/dist-packages/tensorflow/python/autograph/impl/api.py in wrapper(*args, **kwargs)
    690       try:
    691         with conversion_ctx:
--> 692           return converted_call(f, args, kwargs, options=options)
    693       except Exception as e:  # pylint:disable=broad-except
    694         if hasattr(e, 'ag_error_metadata'):

/usr/local/lib/python3.7/dist-packages/tensorflow/python/autograph/impl/api.py in converted_call(f, args, kwargs, caller_fn_scope, options)
    334   if conversion.is_in_allowlist_cache(f, options):
    335     logging.log(2, 'Allowlisted %s: from cache', f)
--> 336     return _call_unconverted(f, args, kwargs, options, False)
    337 
    338   if ag_ctx.control_status_ctx().status == ag_ctx.Status.DISABLED:

/usr/local/lib/python3.7/dist-packages/tensorflow/python/autograph/impl/api.py in _call_unconverted(f, args, kwargs, options, update_cache)
    461 
    462   if kwargs is not None:
--> 463     return f(*args, **kwargs)
    464   return f(*args)
    465 

/usr/local/lib/python3.7/dist-packages/tensorflow_probability/python/layers/conv_variational.py in call(self, inputs)
    230 
    231     outputs = self._apply_variational_kernel(inputs)
--> 232     outputs = self._apply_variational_bias(outputs)
    233     if self.activation is not None:
    234       outputs = self.activation(outputs)

/usr/local/lib/python3.7/dist-packages/tensorflow_probability/python/layers/conv_variational.py in _apply_variational_bias(self, inputs)
    386                                 [outputs_shape[0], outputs_shape[1],
    387                                  outputs_shape[2] * outputs_shape[3],
--> 388                                  outputs_shape[4]])
    389         outputs_4d = tf.nn.bias_add(outputs_4d,
    390                                     self.bias_posterior_tensor,

/usr/local/lib/python3.7/dist-packages/tensorflow/python/util/dispatch.py in wrapper(*args, **kwargs)
    204     """Call target, and fall back on dispatchers if there is a TypeError."""
    205     try:
--> 206       return target(*args, **kwargs)
    207     except (TypeError, ValueError):
    208       # Note: convert_to_eager_tensor currently raises a ValueError, not a

/usr/local/lib/python3.7/dist-packages/tensorflow/python/ops/array_ops.py in reshape(tensor, shape, name)
    193     A `Tensor`. Has the same type as `tensor`.
    194   """
--> 195   result = gen_array_ops.reshape(tensor, shape, name)
    196   tensor_util.maybe_set_static_shape(result, shape)
    197   return result

/usr/local/lib/python3.7/dist-packages/tensorflow/python/ops/gen_array_ops.py in reshape(tensor, shape, name)
   8396   # Add nodes to the TensorFlow graph.
   8397   _, _, _op, _outputs = _op_def_library._apply_op_helper(
-> 8398         "Reshape", tensor=tensor, shape=shape, name=name)
   8399   _result = _outputs[:]
   8400   if _execute.must_record_gradient():

/usr/local/lib/python3.7/dist-packages/tensorflow/python/framework/op_def_library.py in _apply_op_helper(op_type_name, name, **keywords)
    523         except TypeError as err:
    524           if dtype is None:
--> 525             raise err
    526           else:
    527             raise TypeError(

/usr/local/lib/python3.7/dist-packages/tensorflow/python/framework/op_def_library.py in _apply_op_helper(op_type_name, name, **keywords)
    513                   name=input_arg.name,
    514                   as_ref=input_arg.is_ref,
--> 515                   preferred_dtype=default_dtype)
    516           else:
    517             values = ops.convert_to_tensor(

/usr/local/lib/python3.7/dist-packages/tensorflow/python/profiler/trace.py in wrapped(*args, **kwargs)
    161         with Trace(trace_name, **trace_kwargs):
    162           return func(*args, **kwargs)
--> 163       return func(*args, **kwargs)
    164 
    165     return wrapped

/usr/local/lib/python3.7/dist-packages/tensorflow/python/framework/ops.py in convert_to_tensor(value, dtype, name, as_ref, preferred_dtype, dtype_hint, ctx, accepted_result_types)
   1564 
   1565     if ret is None:
-> 1566       ret = conversion_func(value, dtype=dtype, name=name, as_ref=as_ref)
   1567 
   1568     if ret is NotImplemented:

/usr/local/lib/python3.7/dist-packages/tensorflow/python/framework/constant_op.py in _constant_tensor_conversion_function(v, dtype, name, as_ref)
    337                                          as_ref=False):
    338   _ = as_ref
--> 339   return constant(v, dtype=dtype, name=name)
    340 
    341 

/usr/local/lib/python3.7/dist-packages/tensorflow/python/framework/constant_op.py in constant(value, dtype, shape, name)
    263   """
    264   return _constant_impl(value, dtype, shape, name, verify_shape=False,
--> 265                         allow_broadcast=True)
    266 
    267 

/usr/local/lib/python3.7/dist-packages/tensorflow/python/framework/constant_op.py in _constant_impl(value, dtype, shape, name, verify_shape, allow_broadcast)
    281       tensor_util.make_tensor_proto(
    282           value, dtype=dtype, shape=shape, verify_shape=verify_shape,
--> 283           allow_broadcast=allow_broadcast))
    284   dtype_value = attr_value_pb2.AttrValue(type=tensor_value.tensor.dtype)
    285   attrs = {"value": tensor_value, "dtype": dtype_value}

/usr/local/lib/python3.7/dist-packages/tensorflow/python/framework/tensor_util.py in make_tensor_proto(values, dtype, shape, verify_shape, allow_broadcast)
    551       raise TypeError("Failed to convert object of type %s to Tensor. "
    552                       "Contents: %s. Consider casting elements to a "
--> 553                       "supported type." % (type(values), values))
    554     tensor_proto.string_val.extend(str_values)
    555     return tensor_proto

TypeError: Failed to convert object of type <class 'list'> to Tensor. Contents: [None, 16, 16384, 128]. Consider casting elements to a supported type.

I know the error is arising from layer = tfp.layers.Convolution3DFlipout(n_filters, kernel, padding=padding, strides=strides,data_format='channels_first')(input_layer). Default data_format in Convolution3DFlipout is 'channels_last'. When I change it to data_format='channels_first', it started to throw this.

What am I doing wrong here?


Solution

  • If you inspect the following line from the source code:

    outputs_shape = outputs.shape.as_list()
    outputs_4d = tf.reshape(outputs,
                           [outputs_shape[0], outputs_shape[1],
                           outputs_shape[2] * outputs_shape[3],
                           outputs_shape[4]])
    

    So your Convolution has 16 filters, and according to the reshaping 128*128 = 16384 which explains the shape in the error above.

    The workaround is, you can edit line:

    outputs_shape = outputs.shape.as_list()
    

    To:

    outputs_shape = tf.shape(outputs)
    

    Here outputs.shape was static, with tf.shape it is dynamic now. I've run some unit tests with the following change, everything seemed fine so far.

    Reproducible example, before changing:

    import tensorflow as tf
    import tensorflow_probability as tfp
    
    print(tf.__version__) # 2.5.0
    print(tfp.__version__) # 0.13.0
    
    inputs = (3,32,32,32)
    
    model2 = tf.keras.Sequential([
        tf.keras.layers.Input(shape = inputs),
        tfp.layers.Convolution3DFlipout(
            64, kernel_size=5, padding='SAME', activation=tf.nn.relu,
            data_format = 'channels_first'),
        tf.keras.layers.MaxPooling3D(pool_size=(2, 2, 2),
                                     strides=(2, 2, 2),
                                     padding='SAME'),
        tf.keras.layers.Flatten(),
        tfp.layers.DenseFlipout(10),
    ])
    
    TypeError: Failed to convert object of type <class 'list'> to Tensor. Contents: [None, 64, 1024, 32]. Consider casting elements to a supported type.
    

    After changing to following line above in the source code model.summary() shows:

    Model: "sequential"
    _________________________________________________________________
    Layer (type)                 Output Shape              Param #   
    =================================================================
    conv3d_flipout (Conv3DFlipou (None, 64, 32, 32, 32)    48064     
    _________________________________________________________________
    max_pooling3d (MaxPooling3D) (None, 32, 16, 16, 32)    0         
    _________________________________________________________________
    flatten (Flatten)            (None, 262144)            0         
    _________________________________________________________________
    dense_flipout (DenseFlipout) (None, 10)                5242890   
    =================================================================
    Total params: 5,290,954
    Trainable params: 5,290,954
    Non-trainable params: 0