tensorflow, How get value from Tensor - python

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?)

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)
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())

Related

Error: index 255 is out of bounds for axis 1 with size 2 error in preprocessing

I am applying the semantic segmentation and encounter the problem "index 255 is out of bounds for axis 1 with size 2 error in preprocessing" I have two class, building class and background.
While running the "x, y = train_img_gen.next()" it throws me this error.
Can anybody help me. I have tried few things but nothing is working.enter image description here
"""
Define Generator for images and masks so we can read them directly from the drive.
seed=24
batch_size= 16
n_classes=2
from sklearn.preprocessing import MinMaxScaler
scaler = MinMaxScaler()
from tensorflow.keras.utils import to_categorical
#Use this to preprocess input for transfer learning
BACKBONE = 'resnet34'
preprocess_input = sm.get_preprocessing(BACKBONE)
def preprocess_data(img, mask, num_class):
img = scaler.fit_transform(img.reshape(-1, img.shape[-1])).reshape(img.shape)
img = preprocess_input(img)
mask = to_categorical(mask, num_class)
return (img,mask)
#Define the generator.
from tensorflow.keras.preprocessing.image import ImageDataGenerator
def trainGenerator(train_img_path, train_mask_path, num_class):
img_data_gen_args = dict(horizontal_flip=True,
vertical_flip=True,
fill_mode='reflect')
image_datagen = ImageDataGenerator(**img_data_gen_args)
mask_datagen = ImageDataGenerator(**img_data_gen_args)
image_generator = image_datagen.flow_from_directory(
train_img_path,
class_mode = None,
batch_size = batch_size,
seed = seed)
mask_generator = mask_datagen.flow_from_directory(
train_mask_path,
class_mode = None,
color_mode = 'grayscale',
batch_size = batch_size,
seed = seed)
train_generator = zip(image_generator, mask_generator)
for (img, mask) in train_generator:
img, mask = preprocess_data(img, mask, num_class)
yield (img, mask)
train_img_path = "/content/AerialImageDataset/train/data_for_training_and_testing/train_images/"
train_mask_path = "/content/AerialImageDataset/train/data_for_training_and_testing/train_masks/"
train_img_gen = trainGenerator(train_img_path, train_mask_path, num_class=2)
val_img_path = "/content/AerialImageDataset/train/data_for_training_and_testing/val_images/"
val_mask_path = "/content/AerialImageDataset/train/data_for_training_and_testing/val_masks/"
val_img_gen = trainGenerator(val_img_path, val_mask_path, num_class=2)
x, y = train_img_gen.__next__()
"""

How to set possbility to tf.keras.layers.RandomFlip?

Is there possible to set a possibility when doing random flip operations by using tf.keras.layers.RandomFlip ?
for example:
def augmentation():
data_augmentation = keras.Sequential([
keras.layers.RandomFlip("horizontal", p=0.5),
keras.layers.RandomRotation(0.2, p=0.5)
])
return data_augmentation
Try creating a simple Lambda layer and defining your probability in a separate function:
import random
def random_flip_on_probability(image, probability= 0.5):
if random.random() < probability:
return tf.image.random_flip_left_right(image)
return image
def augmentation():
data_augmentation = keras.Sequential([
keras.layers.Lambda(random_flip_on_probability),
keras.layers.RandomRotation(0.2, p=0.5)
])
return data_augmentation
If you need to use data augmentation during training or inference, you will have to define your own custom layer. Try something like this:
import tensorflow as tf
import pathlib
class RandomFlipOnProbability(tf.keras.layers.Layer):
def __init__(self, probability):
super(RandomFlipOnProbability, self).__init__()
self.probability = probability
def call(self, images):
return tf.cond(tf.random.uniform(()) < self.probability, lambda: tf.image.flip_left_right(images), lambda: images)
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 = 32
train_ds = tf.keras.utils.image_dataset_from_directory(
data_dir,
validation_split=0.2,
subset="training",
seed=123,
image_size=(180, 180),
batch_size=batch_size)
random_layer = RandomFlipOnProbability(probability = 0.9)
normalization_layer = tf.keras.layers.Rescaling(1./255)
images, _ = next(iter(train_ds.take(1)))
images = normalization_layer(random_layer(images))
image = images[0]
plt.imshow(image.numpy())

python : keras package : (ValueError: No such layer: fc1)

when i tryed to execute my python code, i get this error: (ValueError: No such layer: fc1) : error capture
i use in my code TensorFlow and Keras package to detect Object in image and return the similar images from custom Dataset.
it s work perfectly on local, but when i trayed in the server OVH there is always the error
(i trayed to change the layer to 'block5_pool' but it's not working with my code.)
my code :
from tensorflow.keras.preprocessing import image
from tensorflow.keras.applications.vgg16 import VGG16, preprocess_input
from tensorflow.keras.models import Model
import numpy as np
from PIL import Image
from datetime import datetime
from flask import Flask, request, render_template
from pathlib import Path
class FeatureExtractor:
def __init__(self):
base_model = VGG16(weights='imagenet', include_top=False)
self.model = Model(inputs=base_model.input, outputs=base_model.get_layer('fc1').output)
def extract(self, img):
"""
Extract a deep feature from an input image
Args:
img: from PIL.Image.open(path) or tensorflow.keras.preprocessing.image.load_img(path)
Returns:
feature (np.ndarray): deep feature with the shape=(4096, )
"""
img = img.resize((224, 224))
img = img.convert('RGB')
x = image.img_to_array(img)
x = np.expand_dims(x, axis=0)
x = preprocess_input(x)
feature = self.model.predict(x)[0]
return feature / np.linalg.norm(feature)
path = "/home/virtuag/www/storage/searchSCB.jpg"
img = Image.open(path)
app = Flask(__name__)
fe = FeatureExtractor()
features = []
img_paths = []
for feature_path in Path("/home/virtuag/www/storage/images_article").glob("*.npy"):
features.append(np.load(feature_path))
img_paths.append(Path("/home/virtuag/www/storage/images_article") / (feature_path.stem + ".jpg"))
features = np.array(features)
query = fe.extract(img)
dists = np.linalg.norm(features-query, axis=1) # L2 distances to features
ids = np.argsort(dists)[:30] # Top 30 results
scores = [img_paths[id] for id in ids]
print (scores)```
thank you
from tensorflow.keras.preprocessing import image
from tensorflow.keras.applications.vgg16 import VGG16, preprocess_input
from tensorflow.keras.models import Model
import numpy as np
from PIL import Image
#from feature_extractor import FeatureExtractor
from datetime import datetime
from flask import Flask, request, render_template
from pathlib import Path
from keras.optimizers import Adam
from tensorflow.keras.layers import Dropout, Dense, Activation, Flatten
class FeatureExtractor:
def __init__(self):
input_shape = (224, 224, 3)
base_model = VGG16(weights='imagenet', include_top=False, input_shape=input_shape)
for layer in base_model.layers:
layer.trainable = False
last = base_model.layers[-1].output
x = Flatten()(last)
x = Dense(1000, activation='relu', name='fc1')(x)
x = Dropout(0.3)(x)
x = Dense(10, activation='softmax', name='predictions')(x)
model = Model(base_model.input, x)
model.compile(optimizer=Adam(lr=0.001),
loss = 'categorical_crossentropy',metrics=['accuracy'])
self.model = Model(inputs=base_model.input, outputs=base_model.layers[-1].output)
def extract(self, img):
"""
Extract a deep feature from an input image
Args:
img: from PIL.Image.open(path) or tensorflow.keras.preprocessing.image.load_img(path)
Returns:
feature (np.ndarray): deep feature with the shape=(4096, )
"""
img = img.resize((224, 224))
img = img.convert('RGB')
x = image.img_to_array(img)
x = np.expand_dims(x, axis=0)
x = preprocess_input(x)
feature = self.model.predict(x)[0]
return feature / np.linalg.norm(feature)
path = "/home/virtuag/www/storage/searchSCB.jpg"
#path = "c:/xamppp/htdocs/projet/V-stock/PWA/public/storage/searchSCB.jpg"
img = Image.open(path)
app = Flask(__name__)
fe = FeatureExtractor()
features = []
img_paths = []
for feature_path in Path("/home/virtuag/www/storage/images_article").glob("*.npy"):
#for feature_path in Path("c:/xamppp/htdocs/projet/V-stock/PWA/public/storage/images_article").glob("*.npy"):
features.append(np.load(feature_path))
#img_paths.append(Path("c:/xamppp/htdocs/projet/V-stock/PWA/public/storage/images_article") / (feature_path.stem + ".jpg"))
img_paths.append(Path("/home/virtuag/www/storage/images_article") / (feature_path.stem + ".jpg"))
features = np.array(features)
query = fe.extract(img)
dists = np.linalg.norm(features-query, axis=1)
ids = np.argsort(dists)[:30]
scores = [img_paths[id] for id in ids]
#print (img_paths)
#print(query)
and the error :
raceback (most recent call last): File "server.py", line 71, in <module> scores = [img_paths[id] for id in ids] File "server.py", line 71, in <listcomp> scores = [img_paths[id] for id in ids] TypeError: only integer scalar arrays can be converted to a scalar index

Getting truth value of array with more than one element in ambigous for albuementation transform

I am using albumentations for applying transform to a Pytorch model but getting this error and I m not getting any clue of what this error is about. Only thing I know is this is occuring due to transform which is being applied but not sure what is wrong with that.
ValueError: Traceback (most recent call last):
File "/opt/conda/lib/python3.6/site-packages/torch/utils/data/_utils/worker.py", line 99, in _worker_loop
samples = collate_fn([dataset[i] for i in batch_indices])
File "/opt/conda/lib/python3.6/site-packages/torch/utils/data/_utils/worker.py", line 99, in <listcomp>
samples = collate_fn([dataset[i] for i in batch_indices])
File "<ipython-input-23-119ea6bc360e>", line 24, in __getitem__
image = self.transform(image)
File "/opt/conda/lib/python3.6/site-packages/albumentations/core/composition.py", line 164, in __call__
need_to_run = force_apply or random.random() < self.p
ValueError: The truth value of an array with more than one element is ambiguous. Use a.any() or a.all()
This is are the snippets of code.
Dataloader getitem() method:
image = cv2.imread(p_path)
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
image = crop_image_from_gray(image)
image = cv2.resize(image, (IMG_SIZE, IMG_SIZE))
image = cv2.addWeighted ( image,4, cv2.GaussianBlur( image , (0,0) , 10) ,-4 ,128)
print(image.shape)
image = self.transform(image)
transforms applied :
val_transform = albumentations.Compose([
Normalize(
mean=[0.485, 0.456, 0.406],
std=[0.229, 0.224, 0.225],
),
ToTensor()
])
The class is called by:
valset = MyDataset(val_df, transform = val_transform)
From official albumentation documentation, you can apply transformation to image
from PIL import Image
import cv2
import numpy as np
from torch.utils.data import Dataset
from torchvision import transforms
from albumentations import Compose, RandomCrop, Normalize, HorizontalFlip, Resize
from albumentations.pytorch import ToTensor
class AlbumentationsDataset(Dataset):
"""__init__ and __len__ functions are the same as in TorchvisionDataset"""
def __init__(self, file_paths, labels, transform=None):
self.file_paths = file_paths
self.labels = labels
self.transform = transform
def __len__(self):
return len(self.file_paths)
def __getitem__(self, idx):
label = self.labels[idx]
file_path = self.file_paths[idx]
# Read an image with OpenCV
image = cv2.imread(file_path)
# By default OpenCV uses BGR color space for color images,
# so we need to convert the image to RGB color space.
image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
image = crop_image_from_gray(image)
image = cv2.resize(image, (IMG_SIZE, IMG_SIZE))
image = cv2.addWeighted ( image,4, cv2.GaussianBlur( image , (0,0) , 10) ,-4 ,128)
image = Img.fromarray(image, mode='RGB')
if self.transform:
augmented = self.transform(image=np.array(image))
image = augmented['image']
image = np.transpose(image, (2, 0, 1))
return image, label
albumentations_transform = Compose([
Normalize(
mean=[0.485, 0.456, 0.406],
std=[0.229, 0.224, 0.225],
),
ToTensor()
])
albumentations_dataset = AlbumentationsDataset(
file_paths=['./images/image_1.jpg', './images/image_2.jpg', './images/image_3.jpg'],
labels=[1, 2, 3],
transform=albumentations_transform,
)
test_loader = DataLoader(dataset = albumentations_dataset, batch_size=4, drop_last=False, shuffle=False).

Tensorflow pretrained model import error

I am working on an object detection model in tensorflow. I have a file model.py:
from PIL import Image
import cv2
import numpy as np
import tensorflow as tf
from .squeezenet import SqueezeNet
save_path = "sqnet/squeezenet.ckpt"
sess = tf.Session()
model = SqueezeNet(save_path=save_path, sess=sess)
class Finder(object):
def __init__(self, image_path):
self.image_path = image_path
def predict(self):
image = process(self.image_path)
ans = sess.run(model.classifier, feed_dict={model.image:
image})
return ans
def process(path):
image = Image.open(path)
# image.show()
image = np.array(image)
image = cv2.resize(image, dsize=(224, 224),
interpolation=cv2.INTER_CUBIC)
image = image.reshape((1, 224, 224, 3))
#print(image.shape)
#img = Image.fromarray(image, 'RGB')
return image
image_path = "/home/jatin/ai.jpeg"
object_detector = Finder(image_path)
ans = object_detector.predict()
print(np.argmax(ans))
sess.close()
I have a folder named sqnet alongside the model.py file within which I have squuezenet.cpkt file. But running this gives the error:
InvalidArgumentError (see above for traceback): Unsuccessful
TensorSliceReader constructor: Failed to get matching files on
sqnet/squeezenet.ckpt: Not found: sqnet; No such file or directory.
What could be the issue?
Seems like a simple IO error to me. Have you tried using absolute path?
save_path = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'sqnet', 'squeezenet.ckpt')

Categories