Search code examples
pythonimage-processingtensorflow2.0tensorflow-datasets

TypeError: <tf.Tensor ... has type <class 'tensorflow.python.framework.ops.EagerTensor'>, but expected one of: numbers.Real


I am writing a function to save images to TFRecord files in order to then read then using the Data API of TensorFlow. However, when trying to create a TFRecord to save it, I receive the following error message:

TypeError: <tf.Tensor ...> has type <class 'tensorflow.python.framework.ops.EagerTensor'>, but expected one of: numbers.Real

The function used to create the TFRecord is:

def create_tfrecord(filepath, label):
    
    image = tf.io.read_file(filepath)
    image = tf.image.decode_jpeg(image, channels=1)
    image = tf.image.convert_image_dtype(image, tf.float32)
    image = tf.image.resize(image, [299, 299])
    
    tfrecord = Example(
        features = Features(
            feature = {
                'image' : Feature(float_list=FloatList(value=[image])),
                'label' : Feature(int64_list=Int64List(value=[label]))
    })).SerializeToString()
    
    return tfrecord

If you need additional information, please let me know.


Solution

  • The problem is that image is a tensor but you need a list of float values. Try something like this:

    import tensorflow as tf
    
    def create_tfrecord(filepath, label):
        
        image = tf.io.read_file(filepath)
        image = tf.image.decode_jpeg(image, channels=1)
        image = tf.image.convert_image_dtype(image, tf.float32)
        image = tf.image.resize(image, [299, 299])
        
        tfrecord = tf.train.Example(
            features = tf.train.Features(
                feature = {
                    'image' : tf.train.Feature(float_list=tf.train.FloatList(value=image.numpy().ravel().tolist())),
                    'label' : tf.train.Feature(int64_list=tf.train.Int64List(value=[label]))
        })).SerializeToString()
        
        return tfrecord
    
    create_tfrecord('/content/result_image.png', 1)
    

    Dummy data was created like this:

    import numpy
    from PIL import Image
    
    imarray = numpy.random.rand(300,300,3) * 255
    im = Image.fromarray(imarray.astype('uint8')).convert('RGB')
    im.save('result_image.png')
    

    If you want to reproduce this example. When loading the tf-record, you just have to reshape the image to its original size.