Ejemplo n.º 1
0
def run_test_harness():
    # define model
    model = define_model()
    # create data generator
    datagen = ImageDataGenerator(featurewise_center=True)
    # specify imagenet mean values for centering
    datagen.mean = [123.68, 116.779, 103.939]
    # prepare iterator
    train_it = datagen.flow_from_directory('../dataset/train/',
                                           class_mode='binary',
                                           batch_size=64,
                                           target_size=(224, 224))
    test_it = datagen.flow_from_directory('../dataset/test/',
                                          class_mode='binary',
                                          batch_size=64,
                                          target_size=(224, 224))
    # fit model
    history = model.fit_generator(train_it,
                                  steps_per_epoch=len(train_it),
                                  validation_data=test_it,
                                  validation_steps=len(test_it),
                                  epochs=1,
                                  verbose=1)
    # evaluate model
    _, acc = model.evaluate_generator(test_it, steps=len(test_it), verbose=0)
    print('> %.3f' % (acc * 100.0))
    # learning curves
    summarize_diagnostics(history)
    model.save('model.h5')
def run_test_harness_3():

    ################################# TRANSFERR LEARNING ############
    ##########################################################################

    model = vgg16_pretrained()
    # create data generator
    datagen = ImageDataGenerator(featurewise_center=True)
    # specify imagenet mean values for centering
    datagen.mean = [123.68, 116.779, 103.939]
    # prepare iterator
    train_it = datagen.flow_from_directory('q7_img_224/train/',
                                           class_mode='binary',
                                           batch_size=10,
                                           target_size=(224, 224))
    test_it = datagen.flow_from_directory('q7_img_224/test/',
                                          class_mode='binary',
                                          batch_size=10,
                                          target_size=(224, 224))
    # fit model
    history = model.fit_generator(train_it,
                                  steps_per_epoch=len(train_it),
                                  validation_data=test_it,
                                  validation_steps=len(test_it),
                                  epochs=10,
                                  verbose=1)
    # evaluate model
    _, acc = model.evaluate_generator(test_it, steps=len(test_it), verbose=1)
    print('> %.3f' % (acc * 100.0))
    # learning curves
    summarize_diagnostics(history)
Ejemplo n.º 3
0
def get_test_generator(df,
                       grab_mean_std,
                       labels,
                       img_dir,
                       H,
                       W,
                       img_col='Image',
                       is_tv_col='Is_tv',
                       batch_size=8,
                       seed=1):
    image_test_gen = ImageDataGenerator(featurewise_center=True,
                                        featurewise_std_normalization=True)
    image_test_gen.mean, image_test_gen.std = grab_mean_std

    test_gen = image_test_gen.flow_from_dataframe(
        dataframe=df[df[is_tv_col] == False],
        directory=img_dir,
        x_col=img_col,
        y_col=labels,
        class_mode='raw',
        batch_size=batch_size,
        shuffle=False,
        seed=seed,
        target_size=(W, H))
    return test_gen
Ejemplo n.º 4
0
def run_test_harness():

    model = define_model()  # define model
    datagen = ImageDataGenerator(
        featurewise_center=True)  # create data generator
    datagen.mean = [123.68, 116.779,
                    103.939]  # specify imagenet mean values for centering

    # prepare iterator
    print("start allocate")
    train_it = datagen.flow_from_directory('/PATH_TO_TRAIN_DIR/',
                                           class_mode='binary',
                                           batch_size=64,
                                           target_size=(240, 320))
    test_it = datagen.flow_from_directory('/PATH_TO_TEST_DIR/',
                                          class_mode='binary',
                                          batch_size=64,
                                          target_size=(240, 320))

    # fit model
    print("start train")
    history = model.fit(train_it,
                        steps_per_epoch=len(train_it),
                        validation_data=test_it,
                        validation_steps=len(test_it),
                        epochs=20,
                        verbose=1)
    model.save('/PATH_TO_MODEL_.h5_FILE')

    # evaluate model
    _, acc = model.evaluate(test_it, steps=len(test_it), verbose=0)
    print('> %.3f' % (acc * 100.0))
    # learning curves
    summarize_diagnostics(history)
Ejemplo n.º 5
0
def get_tv_generator(df,
                     fold_train,
                     fold_val,
                     grab_mean_std,
                     labels,
                     img_dir,
                     H,
                     W,
                     img_col='Image',
                     shuffle=True,
                     batch_size=8,
                     seed=1):
    image_train_gen = ImageDataGenerator(featurewise_center=True,
                                         featurewise_std_normalization=True,
                                         rotation_range=7,
                                         zoom_range=0.1,
                                         horizontal_flip=True,
                                         validation_split=0.)
    image_train_gen.mean, image_train_gen.std = grab_mean_std

    train_gen = image_train_gen.flow_from_dataframe(
        dataframe=df[df['Image'].isin(fold_train)],
        directory=img_dir,
        x_col=img_col,
        y_col=labels,
        class_mode='raw',
        batch_size=batch_size,
        shuffle=shuffle,
        seed=seed,
        target_size=(W, H))

    image_val_gen = ImageDataGenerator(featurewise_center=True,
                                       featurewise_std_normalization=True)
    image_val_gen.mean, image_val_gen.std = grab_mean_std

    val_gen = image_val_gen.flow_from_dataframe(
        dataframe=df[df['Image'].isin(fold_val)],
        directory=img_dir,
        x_col=img_col,
        y_col=labels,
        class_mode='raw',
        batch_size=batch_size,
        shuffle=False,
        seed=seed,
        target_size=(W, H))
    return train_gen, val_gen
Ejemplo n.º 6
0
def main():

    model_path = "./model.h5"
    checkpoint = ModelCheckpoint(model_path,
                                 monitor='val_loss',
                                 mode='min',
                                 save_best_only='True',
                                 verbose=1)

    model = VGG16(include_top=False, input_shape=(224, 224, 3))

    for layer in model.layers:
        layer.trainable = False

    flat1 = Flatten()(model.layers[-1].output)
    class1 = Dense(128, activation='relu',
                   kernel_initializer='he_uniform')(flat1)
    output = Dense(1, activation='sigmoid')(class1)
    model = Model(inputs=model.inputs, outputs=output)

    opt = SGD(lr=0.001, momentum=0.9)
    model.compile(optimizer=opt,
                  loss='binary_crossentropy',
                  metrics=['accuracy'])

    datagen = ImageDataGenerator(featurewise_center=True)
    datagen.mean = [123.68, 116.779, 103.939]

    train_it = datagen.flow_from_directory('dataset_dogs_vs_cats/train/',
                                           class_mode='binary',
                                           batch_size=16,
                                           target_size=(224, 224))
    test_it = datagen.flow_from_directory('dataset_dogs_vs_cats/test/',
                                          class_mode='binary',
                                          batch_size=16,
                                          target_size=(224, 224))

    model.fit_generator(train_it,
                        steps_per_epoch=len(train_it),
                        validation_data=test_it,
                        validation_steps=len(test_it),
                        epochs=10,
                        callbacks=[checkpoint],
                        verbose=1)

    user_input = input("Do you want to evaluate the model on the test set?\
                       (y/n)")

    if user_input == 'y':
        score = model.evaluate_generator(test_it,
                                         steps=len(test_it),
                                         verbose=1)
        print("loss: ", score[0])
        print('accuracy: ', score[1])
Ejemplo n.º 7
0
def create_prediction_model(npz_filename, model_name):
    # load dataset
    X, y = load_dataset(npz_filename)
    # create data generator
    datagen = ImageDataGenerator(featurewise_center=True,
                                 horizontal_flip=True,
                                 vertical_flip=True,
                                 rotation_range=90)
    # specify imagenet mean values for centering
    datagen.mean = [123.68, 116.779, 103.939]
    # prepare iterator
    train_it = datagen.flow(X, y, batch_size=128)
    # define model
    model = define_model()
    # fit model
    model.fit(train_it, steps_per_epoch=len(train_it), epochs=50, verbose=0)
    # save model
    model.save(model_name)
def run_test_harness():
    modelName = 'nasnetMobile_5species75train25'
    # define model
    model = define_model()
    # create data generator
    datagen = ImageDataGenerator(featurewise_center=True)
    # specify imagenet mean values for centering
    datagen.mean = [123.68, 116.779, 103.939]
    # prepare iterators
    train_it = datagen.flow_from_directory('5species75train25test/train',
                                           class_mode='categorical',
                                           batch_size=32,
                                           target_size=(224, 224))
    test_it = datagen.flow_from_directory('5species75train25test/test',
                                          class_mode='categorical',
                                          batch_size=32,
                                          target_size=(224, 224))
    # fit model
    history = model.fit(train_it,
                        steps_per_epoch=len(train_it),
                        validation_data=test_it,
                        validation_steps=len(test_it),
                        epochs=20,
                        verbose=1)

    # save model (.h5 format)
    model.save(modelName + '.h5')

    # save model (.pb format)
    model.save(modelName)

    # evaluate model
    _, acc = model.evaluate(test_it, steps=len(test_it), verbose=1)
    print('> %.3f' % (acc * 100.0))

    # plot model
    plot_model(model, to_file=modelName + '.png')

    # learning curves
    summarize_diagnostics(history)
Ejemplo n.º 9
0
#optimizer = RMSprop(lr=0.0008, decay=1e-6)
model.compile(optimizer=optimizer,
			loss='categorical_crossentropy',
			metrics=['accuracy'])

# this is the augmentation we will use for training
train_datagen = ImageDataGenerator(
    rescale=1. / 255,
    featurewise_center=True,
    featurewise_std_normalization=True,
    horizontal_flip=True,
    vertical_flip=True,
    rotation_range=15,
    width_shift_range=0.1,
    height_shift_range=0.1)
train_datagen.mean = GetCifar10Mean()
train_datagen.std = GetCifar10STD() 

test_datagen = ImageDataGenerator(rescale=1. / 255,
    featurewise_center=True,
    featurewise_std_normalization=True) 
test_datagen.mean = GetCifar10Mean()
test_datagen.std = GetCifar10STD()

train_generator = train_datagen.flow_from_directory(
    train_data_dir,
    target_size=(img_width, img_height),
    color_mode='rgb',
    batch_size=batch_size,
    class_mode='categorical')
Ejemplo n.º 10
0
def train_and_evaluate(args):

    # load the filenames of all room_scenes as classes for classification
    classes = util.load_classes(args)

    # load data labels
    df_labels = util.make_labels_df(args)
    df_train, df_test = train_test_split(df_labels, test_size=0.1)

    # create data generator
    train_datagen = ImageDataGenerator(featurewise_center=True,
                                       horizontal_flip=True,
                                       vertical_flip=True,
                                       rotation_range=90)
    test_datagen = ImageDataGenerator(featurewise_center=True)

    # specify imagenet mean values for centering
    train_datagen.mean = [123.68, 116.779, 103.939]
    test_datagen.mean = [123.68, 116.779, 103.939]

    # prepare iterators
    train_it = train_datagen.flow_from_dataframe(dataframe=df_train,
                                                 directory=os.path.join(
                                                     args.data_dir, 'images'),
                                                 x_col="file_name",
                                                 y_col="room_name",
                                                 batch_size=args.batch_size,
                                                 seed=42,
                                                 shuffle=True,
                                                 classes=classes,
                                                 class_mode="categorical",
                                                 target_size=(128, 128))

    test_it = test_datagen.flow_from_dataframe(dataframe=df_test,
                                               directory=os.path.join(
                                                   args.data_dir, 'images'),
                                               x_col="file_name",
                                               y_col="room_name",
                                               batch_size=args.batch_size,
                                               seed=42,
                                               shuffle=True,
                                               classes=classes,
                                               class_mode="categorical",
                                               target_size=(128, 128))

    # define model
    print('> Define model')
    keras_model = model.create_model()

    # fit model
    print('> Begin training')
    print('> len(train_it) = {}'.format(len(train_it)))
    print('> len(test_it) = {}'.format(len(test_it)))

    history = keras_model.fit_generator(train_it,
                                        steps_per_epoch=len(train_it),
                                        validation_data=test_it,
                                        validation_steps=len(test_it),
                                        epochs=args.num_epochs,
                                        verbose=1)

    # evaluate model
    print('> Begin evaluating')
    loss, fbeta = keras_model.evaluate_generator(test_it,
                                                 steps=len(test_it),
                                                 verbose=1)
    print('> loss=%.3f, fbeta=%.3f' % (loss, fbeta))

    # save model
    if not os.path.exists(args.out_dir):
        os.makedirs(args.out_dir)
    keras_model.save(os.path.join(args.out_dir, 'final_model.h5'))

    # learning curves
    util.summarize_diagnostics(history,
                               os.path.join(args.out_dir, 'diagnostics.png'))
Ejemplo n.º 11
0
 def generate_predictions(self, model, data):
     self.test_image_augmentations = {}
     if 'zca_whitening' in self.image_augmentations.keys():
         if self.image_augmentations['zca_whitening']:
             self.test_image_augmentations['zca_whitening'] = True
     if self.img_norm == 'mean_and_std':
         self.test_image_augmentations['featurewise_center'] = True
         self.test_image_augmentations[
             'featurewise_std_normalization'] = True
     test_datagen = ImageDataGenerator(
         preprocessing_function=self.preprocess_input,
         **self.test_image_augmentations)
     if self.img_norm == 'mean_and_std':
         if self.greyscale:
             test_datagen.mean = np.array(self.img_mean_pt,
                                          dtype=np.float32)
             test_datagen.std = np.array(self.img_std_pt, dtype=np.float32)
         else:
             test_datagen.mean = np.array(self.img_mean_pt,
                                          dtype=np.float32).reshape(
                                              (1, 1,
                                               3))  # ordering: [R, G, B]
             test_datagen.std = np.array(self.img_std_pt,
                                         dtype=np.float32).reshape(
                                             (1, 1,
                                              3))  # ordering: [R, G, B]
     # Create Data Generators
     if self.greyscale:
         valid_generator = test_datagen.flow_from_dataframe(
             dataframe=data,
             directory=None,
             x_col=self.x_name,
             y_col=self.y_name,
             batch_size=self.batch_size,
             seed=self.random_state,
             shuffle=False,
             class_mode="other",
             target_size=(self.model_img_width, self.model_img_height),
             color_mode='grayscale')
     else:
         valid_generator = test_datagen.flow_from_dataframe(
             dataframe=data,
             directory=None,
             x_col=self.x_name,
             y_col=self.y_name,
             batch_size=self.batch_size,
             seed=self.random_state,
             shuffle=False,
             class_mode="other",
             target_size=(self.model_img_width, self.model_img_height))
     # Predict
     if self.norm_labels:
         print(f"mean: {self.mean_pt} std: {self.std_pt}")
         return model.predict_generator(
             valid_generator,
             steps=np.ceil(len(data) / self.batch_size),
             verbose=1) * self.std_pt + self.mean_pt
     else:
         return model.predict_generator(valid_generator,
                                        steps=np.ceil(
                                            len(data) / self.batch_size),
                                        verbose=1)
                        shear_range=0.2,
                        zoom_range=0.2,
                        horizontal_flip=True,
                        fill_mode='nearest',
                        featurewise_center=True # this is to use the mean substraction of ImageNet
                    )

datagen_validation = ImageDataGenerator(
                        rescale=1/255,
                        featurewise_center=True # this is to use the mean substraction of ImageNet
                    )

# define the ImageNet mean subtraction (in RGB order) and set the
# the mean subtraction value for the data augmentation object
imagenet_mean = np.array([123.68, 116.779, 103.939], dtype="float32")
datagen_train.mean = imagenet_mean
datagen_validation.mean = imagenet_mean

train_generator = datagen_train.flow_from_directory(
                    train_data_dir,
                    target_size=(img_width, img_height),
                    batch_size=batch_size,
                    class_mode='categorical',
                    interpolation='lanczos')

validation_generator = datagen_validation.flow_from_directory(
                        validation_data_dir,
                        target_size=(img_width, img_height),
                        batch_size=batch_size,
                        class_mode='categorical',
                        interpolation='lanczos')
Ejemplo n.º 13
0
                                                lbl,
                                                test_size=0.25,
                                                stratify=lbl,
                                                random_state=331)

trDatGen = ImageDataGenerator(rotation_range=30,
                              width_shift_range=0.2,
                              height_shift_range=0.2,
                              zoom_range=0.15,
                              shear_range=0.15,
                              horizontal_flip=True,
                              fill_mode="nearest")

tsDatGen = ImageDataGenerator()

trDatGen.mean = imgMean
tsDatGen.mean = imgMean

# ...........................................................................

optmz = SGD(lr=1e-4, momentum=0.9, decay=1e-4 / 25)

base = ResNet50(weights="imagenet",
                include_top=False,
                input_tensor=Input(shape=(224, 224, 3)))


def createModel():
    h = base.output
    h = AveragePooling2D(pool_size=(7, 7))(h)
    h = Flatten(name="flatten")(h)
Ejemplo n.º 14
0
from tensorflow.keras.preprocessing.image import load_img, img_to_array
from tensorflow.keras.preprocessing.image import ImageDataGenerator
from tensorflow.keras.models import load_model
from tensorflow.compat.v1 import ConfigProto
from tensorflow.compat.v1 import InteractiveSession
import pandas as pd
import numpy as np

config = ConfigProto()
config.gpu_options.allow_growth = True
session = InteractiveSession(config=config)

datagen = ImageDataGenerator(featurewise_center=True)
datagen.mean = [123.68, 116.779, 103.939]

batch_size = 10
iterator = datagen.flow_from_directory('test',
                                       class_mode=None,
                                       batch_size=batch_size,
                                       target_size=(224, 224),
                                       shuffle=False)

model = load_model('model.h5')
results = model.predict_generator(iterator, steps=1, verbose=1)

results_string = list()
for result in results:
    if result == 0.:
        results_string.append('cat')
    else:
        results_string.append('dog')
Ejemplo n.º 15
0
testPath = os.path.sep.join(['..', BASE_PATH, BASE_PATH + TEST])

# nbr total des image dans chacun des repo train test
totalTrain = len(list(paths.list_images(trainPath)))
totalTest = len(list(paths.list_images(testPath)))

# instancier un objet ImageDataGenerator pour l'augmentation des donnees train
# 1. Appliquer une augmentation des données de train, avec un flip horizontal.
trainAug = ImageDataGenerator(horizontal_flip=True)
# instancier un objet ImageDataGenerator pour l'augmentation des donnees test
testAug = ImageDataGenerator()

# 2. Les images en entrée vont être normalisées par rapport à la moyenne des plans RGB des images de ImageNet.
# definir la moyenne des images ImageNet par plan RGB pour normaliser les images de la base Food-11
mean = np.array([123.68, 116.779, 103.939], dtype="float32")
trainAug.mean = mean
testAug.mean = mean

#3. Charger un model pré-appris sur ImageNet sans la dernière couche FC.
#print("[INFO] Chargement de NASNetMobile...")
#baseModel = NASNetMobile(weights="imagenet", include_top=False, input_tensor=Input(shape=(224, 224, 3)))
#print("[INFO] Chargement fini...")
# FCmodel = NASNetMobile(weights="imagenet", include_top=True, input_tensor=Input(shape=(224, 224, 3)))

#4. Faire un model.summary() avec et sans la dernière couche afin de voir la couche à
#redéfinir (un globalaveragepooling, un dropout, un flatten, etc) ceci diffère d’un modèle
#à l’autre.

#print(baseModel.summary())
#print('############################################################################################################')
#print(FCmodel.summary())
Ejemplo n.º 16
0
# initialize the training data augmentation object
trainAug = ImageDataGenerator(rotation_range=30,
                              zoom_range=0.15,
                              width_shift_range=0.2,
                              height_shift_range=0.2,
                              shear_range=0.15,
                              horizontal_flip=True,
                              fill_mode='nearest')

# validation/testing data augmentation object
valAug = ImageDataGenerator()

# TODO - Look into these values
mean = np.array([123.68, 116.779, 103.939], dtype='float32')

trainAug.mean = mean
valAug.mean = mean

# load the ResNet50
baseModel = ResNet50(weights='imagenet',
                     include_top=False,
                     input_tensor=Input(shape=(224, 224, 3)))

# head of model that will go on top of baseModel
headModel = baseModel.output
headModel = AveragePooling2D(pool_size=(7, 7))(headModel)
headModel = Flatten(name='flatten')(headModel)
headModel = Dense(512, activation='relu')(headModel)
headModel = Dropout(0.5)(headModel)
headModel = Dense(len(lb.classes_), activation='softmax')(headModel)
                                                    test_size=0.2,
                                                    shuffle=True)

#%%

data_generator = ImageDataGenerator(rescale=1. / 255,
                                    rotation_range=30,
                                    zoom_range=0.15,
                                    width_shift_range=0.2,
                                    height_shift_range=0.2,
                                    shear_range=0.15,
                                    horizontal_flip=True,
                                    fill_mode="nearest")

mean = np.array([123.68, 116.779, 103.939], dtype="float32")
data_generator.mean = mean

#%%

base_model = ResNet50(weights="imagenet",
                      include_top=False,
                      input_tensor=Input(shape=(*IMAGE_SIZE, 3)))

head_model = base_model.output
head_model = AveragePooling2D(pool_size=(7, 7))(head_model)
head_model = Flatten(name="flatten")(head_model)
head_model = Dense(512, activation="relu")(head_model)
head_model = Dropout(0.5)(head_model)
head_model = Dense(len(lb.classes_), activation="softmax")(head_model)

model = Model(inputs=base_model.input, outputs=head_model)
Ejemplo n.º 18
0
if hvd.rank() == 0:
    callbacks.append(
        ModelCheckpoint(os.path.join(CHECKPOINTS_DIR,
                                     "checkpoint-{epoch}.h5")))

# Set up ImageDataGenerators to do data augmentation for the training images.
train_datagen = ImageDataGenerator(
    rotation_range=15,
    rescale=1.0 / 255,
    shear_range=0.1,
    zoom_range=0.2,
    horizontal_flip=True,
    width_shift_range=0.1,
    height_shift_range=0.1,
)
train_datagen.mean = [123.68, 116.779, 103.939]

train_generator = train_datagen.flow_from_dataframe(
    train_df,
    DATA_PATH,
    x_col="filename",
    y_col="category",
    target_size=IMAGE_SIZE,
    class_mode="binary",
    batch_size=BATCH_SIZE,
)

if hvd.rank() == 0:
    mlctx.logger.info("classes:", train_generator.class_indices)

validation_datagen = ImageDataGenerator(rescale=1.0 / 255)
Ejemplo n.º 19
0
    def train_model(self, model, train_data, test_data):
        # If normalized labels are needed, extract it
        if self.norm_labels:
            train_data[self.y_name] = (train_data[self.y_name] -
                                       self.mean_pt) / self.std_pt
            test_data[self.y_name] = (test_data[self.y_name] -
                                      self.mean_pt) / self.std_pt
        if self.lf_setting == 'weighted_mape':
            self.weight = train_data[self.y_name].max()

        # Create Data Generators
        self.test_image_augmentations = {}
        if 'zca_whitening' in self.image_augmentations.keys():
            if self.image_augmentations['zca_whitening']:
                self.test_image_augmentations['zca_whitening'] = True
        if self.img_norm == 'mean_and_std':
            self.image_augmentations['featurewise_center'] = True
            self.image_augmentations['featurewise_std_normalization'] = True
            self.test_image_augmentations['featurewise_center'] = True
            self.test_image_augmentations[
                'featurewise_std_normalization'] = True
        datagen = ImageDataGenerator(
            preprocessing_function=self.preprocess_input,
            **self.image_augmentations)
        test_datagen = ImageDataGenerator(
            preprocessing_function=self.preprocess_input,
            **self.test_image_augmentations)
        if self.img_norm == 'mean_and_std':
            if self.greyscale:
                datagen.mean = np.array(self.img_mean_pt, dtype=np.float32)
                datagen.std = np.array(self.img_std_pt, dtype=np.float32)
                test_datagen.mean = np.array(self.img_mean_pt,
                                             dtype=np.float32)
                test_datagen.std = np.array(self.img_std_pt, dtype=np.float32)
            else:
                datagen.mean = np.array(self.img_mean_pt,
                                        dtype=np.float32).reshape(
                                            (1, 1, 3))  # ordering: [R, G, B]
                datagen.std = np.array(self.img_std_pt,
                                       dtype=np.float32).reshape(
                                           (1, 1, 3))  # ordering: [R, G, B]
                test_datagen.mean = np.array(self.img_mean_pt,
                                             dtype=np.float32).reshape(
                                                 (1, 1,
                                                  3))  # ordering: [R, G, B]
                test_datagen.std = np.array(self.img_std_pt,
                                            dtype=np.float32).reshape(
                                                (1, 1,
                                                 3))  # ordering: [R, G, B]
        # Set-up callback
        callbacks_list = [
            ModelCheckpoint(self.model_pth, verbose=1, period=5),
            ModelCheckpoint(self.model_best_pth,
                            verbose=1,
                            save_best_only=True),
            CSVLogger(os.path.join(self.output_pth, 'hist.csv'))
        ]
        # Create Data Generators
        if self.greyscale:
            train_generator = datagen.flow_from_dataframe(
                dataframe=train_data,
                directory=None,
                x_col=self.x_name,
                y_col=self.y_name,
                batch_size=self.batch_size,
                seed=self.random_state,
                shuffle=True,
                class_mode="raw",
                target_size=(self.model_img_width, self.model_img_height),
                color_mode='grayscale')
            valid_generator = test_datagen.flow_from_dataframe(
                dataframe=test_data,
                directory=None,
                x_col=self.x_name,
                y_col=self.y_name,
                batch_size=self.batch_size,
                seed=self.random_state,
                shuffle=False,
                class_mode="raw",
                target_size=(self.model_img_width, self.model_img_height),
                color_mode='grayscale')
        else:
            train_generator = datagen.flow_from_dataframe(
                dataframe=train_data,
                directory=None,
                x_col=self.x_name,
                y_col=self.y_name,
                batch_size=self.batch_size,
                seed=self.random_state,
                shuffle=True,
                class_mode="raw",
                target_size=(self.model_img_width, self.model_img_height))
            valid_generator = test_datagen.flow_from_dataframe(
                dataframe=test_data,
                directory=None,
                x_col=self.x_name,
                y_col=self.y_name,
                batch_size=self.batch_size,
                seed=self.random_state,
                shuffle=False,
                class_mode="raw",
                target_size=(self.model_img_width, self.model_img_height))
        H = model.fit_generator(
            generator=train_generator,
            steps_per_epoch=len(train_data) // self.batch_size,
            validation_data=valid_generator,
            validation_steps=len(test_data) // self.batch_size,
            epochs=self.epochs,
            verbose=1,
            callbacks=callbacks_list,
            workers=12)
        return H, model