'Preprocessing for Resnet50 Tensorflow
I am using ImageDataGenerator() and passing tf.keras.applications.preprocessing.resnet50 as the preprocessing argument for ImageDataGenerator().
The original image values are between 0-255. But after the preprocessing, I noticed that the image values are not between 0-1 and I get val_loss: nan. My activation functions are selu and softmax.
Image data value after preprocessing using tf.keras.applications.preprocessing.resnet50
My questions are is tf.keras.applications.preprocessing.resnet50 suppose normalize the data between 0-1?
Am I potentially getting val_loss: nan because my data is not scaled between 0-1?
import matplotlib.pyplot as plt
import os
import pandas as pd
import numpy as np
import PIL
import pathlib
import tensorflow as tf
from tensorflow import keras
from tensorflow.keras import layers
from tensorflow.keras.layers import Dense, Flatten, BatchNormalization, Dropout
from tensorflow.keras.models import Sequential
from tensorflow.keras.preprocessing.image import ImageDataGenerator
from keras.callbacks import EarlyStopping
def ds_generator(h, w, bs, preprocessing):
train_folder = '/home/ec2-user/SageMaker/PCM_Map_Images/train/'
test_folder = '/home/ec2-user/SageMaker/PCM_Map_Images/test/'
dir_train = pathlib.Path(train_folder)
dir_test = pathlib.Path(test_folder)
data_gen = ImageDataGenerator(preprocessing_function=preprocessing, validation_split=0.15)
train_ds = data_gen.flow_from_directory(dir_train, target_size=(h, w), class_mode='sparse',
subset='training', shuffle = False,
seed = 0, batch_size=bs)
val_ds = data_gen.flow_from_directory(dir_train, target_size=(h, w), class_mode='sparse',
subset='validation', shuffle = False,
seed = 0, batch_size=bs)
test_ds = data_gen.flow_from_directory('.', target_size=(h, w), class_mode=None, classes=['test'], shuffle=False,
batch_size=bs)
return train_ds, val_ds, test_ds
resnet50 = tf.keras.applications.resnet50
h, w, c = 32, 32, 3
batch_size = 64
train_ds, val_ds, test_ds = ds_generator(h, w, batch_size, preprocessing=resnet50.preprocess_input)
model = Sequential()
Init = tf.keras.initializers.RandomNormal(seed=0) # seed all that you can
cb = EarlyStopping(monitor='val_loss', restore_best_weights=True, patience=6)
# you execute this line of code if NG made life easier
pre_train_model = tf.keras.applications.ResNet50(include_top=False,
input_shape=(h, w, c),
pooling='max',
weights='resnet50_weights_tf_dim_ordering_tf_kernels_notop.h5')
for layer in pre_train_model.layers[:-25]:
if isinstance(layer, layers.BatchNormalization):
layer.trainable = False
else:
layer.trainable = True
model.add(pre_train_model)
model.add(BatchNormalization())
model.add(Flatten())
model.add(Dense(256, activation='selu', kernel_initializer=Init))
model.add(Dropout(.50))
model.add(BatchNormalization())
model.add(Dense(128, activation='selu', kernel_initializer=Init))
model.add(Dropout(.30))
model.add(BatchNormalization())
model.add(Dense(3, activation='softmax', kernel_initializer=Init))
model.summary()
model.compile(optimizer=tf.keras.optimizers.Nadam(learning_rate=0.01, clipnorm=1.0, beta_1=.01), loss='sparse_categorical_crossentropy', metrics=['accuracy'])
hist = model.fit(train_ds, epochs=6, validation_data=val_ds)
Solution 1:[1]
The NaN is not due to the scaling. Most preprocess functions scale the image pixels between -1 and +1. You can use the code below as a preprocessor function
def preprocess(img)
return img=img/127.5-1
then in ImageDataGenerator use
gen=tf.keras.preprocessing.image.ImageDataGenerator( preprocessing_function=preprocess)
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | Gerry P |
