Search code examples
pythontensorflowkerastensorflow-datasets

tensorflow, How get value from Tensor


I upload the data in BatchDataset using the image_dataset_from_directory method

seed = 64
images = tf.keras.utils.image_dataset_from_directory(
    '/content/drive/MyDrive/DATA_PYTHON/Recognize_Alphabet/Recognize_Alphabet', 
    validation_split=0.2, 
    image_size=(34, 34),
    color_mode='rgb',
    interpolation='nearest',
    subset='training',
    seed=seed)

I want to invert the colors for all the images that I uploaded. To do this, I try to write a method:

def invertColor(im, b):

  sess2 = tf2.Session()
  im = sess2.run(im)

  imI = PIL.ImageOps.invert(im)
  imIN = np.asarray(imI)
  imINC = cv2.cvtColor(imIN, cv2.COLOR_BGR2RGB)
  bI = Image.fromarray(imINC, 'RGB')
  return bI

When I call the map with this invertColor method

images2 = images.map(invertColor)

I'm getting this errors:

InvalidArgumentError: in user code:
File "<ipython-input-19-1f1e09851e25>", line 5, in invertColor  *
    sess2.run(im)

InvalidArgumentError: Graph execution error:

Detected at node 'args_0' defined at (most recent call last):
    File "/usr/lib/python3.7/runpy.py", line 193, in _run_module_as_main
      "__main__", mod_spec)

How can I get the value of im element in the invertColor method? (Or how to invert colors in the BatchDataset?)


Solution

  • You can try using tf.py_function to integrate PIL operations in graph mode. Here is an example with a batch size of 1 to keep it simple (you can change the batch size afterwards):

    Before

    import tensorflow as tf
    import matplotlib.pyplot as plt
    import pathlib
    import PIL
    import cv2
    from PIL import Image
    import PIL.ImageOps    
    import numpy as np
    
    dataset_url = "https://storage.googleapis.com/download.tensorflow.org/example_images/flower_photos.tgz"
    data_dir = tf.keras.utils.get_file('flower_photos', origin=dataset_url, untar=True)
    data_dir = pathlib.Path(data_dir)
    
    batch_size = 1
    
    train_ds = tf.keras.utils.image_dataset_from_directory(
      data_dir,
      validation_split=0.2,
      subset="training",
      seed=123,
      shuffle= False,
      image_size=(180, 180),
      batch_size=batch_size)
    
    image, _ = next(iter(train_ds.take(1)))
    plt.imshow(image[0].numpy() / 255)
    

    enter image description here

    After

    def invert_color(image):
      im = Image.fromarray(image[0].numpy().astype('uint8'), 'RGB')
      imI = PIL.ImageOps.invert(im)
      imIN = np.asarray(imI)
      imINC = cv2.cvtColor(imIN, cv2.COLOR_BGR2RGB)
      return imINC / 255
    
    def change_data(image, label):
      return  tf.py_function(invert_color, [image], Tout=[tf.float32]), label
    
    train_ds = train_ds.map(change_data)
    
    image, _ = next(iter(train_ds.take(1)))
    plt.imshow(image[0].numpy())
    

    enter image description here