Image Classification
Keras
English
art
CNN_And_ELA / cnn_ela_training.py
benjaminStreltzin's picture
Update cnn_ela_training.py
ff08cf1 verified
# -*- coding: utf-8 -*-
"""
Created on Mon Apr 29 17:46:18 2024
@author: beni
"""
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.image as mpimg
from PIL import Image
import os
from pylab import *
import re
from PIL import Image, ImageChops, ImageEnhance
import tensorflow as tf
from sklearn.model_selection import train_test_split
from sklearn.metrics import confusion_matrix
import itertools
from tensorflow.keras.utils import to_categorical
from keras.models import Sequential
from keras.layers import Dense, Dropout, Flatten, Conv2D, MaxPool2D
from tensorflow.keras.optimizers.legacy import RMSprop
from keras.preprocessing.image import ImageDataGenerator
from keras.callbacks import ReduceLROnPlateau, EarlyStopping
from scipy.ndimage import gaussian_filter
def convert_to_ela_image(path, quality, output_dir, resize=(256, 256)):
filename = path
resaved_filename = os.path.join(output_dir, os.path.splitext(os.path.basename(filename))[0] + '.resaved.jpg')
ELA_filename = os.path.join(output_dir, os.path.splitext(os.path.basename(filename))[0] + '.ela.png')
# Open and resize the image
im = Image.open(filename).convert('RGB')
im_resized = im.resize(resize)
# Save the resized image
im_resized.save(resaved_filename, 'JPEG', quality=quality)
resaved_im = Image.open(resaved_filename)
ela_im = ImageChops.difference(im_resized, resaved_im)
extrema = ela_im.getextrema()
max_diff = max([ex[1] for ex in extrema])
if max_diff == 0:
max_diff = 1
scale = 255.0 / max_diff
ela_im = ImageEnhance.Brightness(ela_im).enhance(scale)
ela_im.save(ELA_filename)
return ela_im
def shuffle_and_split_data(dataframe, test_size=0.2, random_state=59):
# Shuffle the DataFrame
shuffled_df = dataframe.sample(frac=1, random_state=random_state).reset_index(drop=True)
# Split the DataFrame into train and validation sets
train_df, val_df = train_test_split(shuffled_df, test_size=test_size, random_state=random_state)
return train_df, val_df
def labeling(path_real, path_fake):
image_paths = []
labels = []
for filename in os.listdir(path_real):
image_paths.append(os.path.join(path_real, filename))
labels.append(0)
for filename in os.listdir(path_fake):
image_paths.append(os.path.join(path_fake, filename))
labels.append(1)
dataset = pd.DataFrame({'image_path': image_paths, 'label': labels})
return dataset
if __name__ == "__main__":
##############################################################
# handling the dataset , set it and label it
np.random.seed(22)
tf.random.set_seed(9)
traning_fake_folder = 'datasets/training_set/fake/'
traning_real_folder = 'datasets/training_set/real/'
traning_ela_output = 'datasets/training_set/ela_output/'
traning_set = labeling(traning_real_folder, traning_fake_folder)
X = []
Y = []
#################################################################
# preprocess the images using ELA method and storing the output.
for index, row in traning_set.iterrows():
X.append(array(convert_to_ela_image(row[0], 90,traning_ela_output).resize((128, 128))).flatten() / 255.0)
Y.append(row[1])
X = np.array(X)
Y = to_categorical(Y, 2)
X = X.reshape(-1, 128, 128, 3)
X_train, X_val, Y_train, Y_val = train_test_split(X, Y, test_size = 0.2, random_state=1,shuffle=True)
################################################################################
# Cnn network creation
model = Sequential()
model.add(Conv2D(filters = 32, kernel_size = (5,5),padding = 'valid',
activation ='relu', input_shape = (128,128,3)))
print("Input: ", model.input_shape)
print("Output: ", model.output_shape)
model.add(Conv2D(filters = 32, kernel_size = (5,5),padding = 'valid',
activation ='relu'))
print("Input: ", model.input_shape)
print("Output: ", model.output_shape)
model.add(MaxPool2D(pool_size=(2,2)))
model.add(Dropout(0.25))
print("Input: ", model.input_shape)
print("Output: ", model.output_shape)
model.add(Flatten())
model.add(Dense(256, activation = "relu"))
model.add(Dropout(0.5))
model.add(Dense(2, activation = "softmax"))
model.summary()
#Define optimizer .
optimizer = RMSprop(lr=0.0005, rho=0.9, epsilon=1e-08, decay=0.0)
#setting the model , loss func , mertics , optimizer.
model.compile(optimizer = optimizer , loss = "categorical_crossentropy", metrics=["accuracy"])
#setting early stopping to train faster.
early_stopping = EarlyStopping(monitor='val_acc',
min_delta=0,
patience=2,
verbose=0, mode='auto')
epochs = 22
batch_size = 100
#####################################################
#running the model , adding the validation set
history = model.fit(X_train, Y_train, batch_size = batch_size, epochs = epochs,
validation_data = (X_val, Y_val), verbose = 2, callbacks=[early_stopping])
#####################################################
#plots and metrics
plt.plot(history.history['accuracy'])
plt.plot(history.history['val_accuracy'])
plt.title('Model accuracy')
plt.xlabel('Epoch')
plt.ylabel('Accuracy')
plt.legend(['Train', 'Validation'], loc='upper left')
plt.show()
# Plot training & validation loss values
plt.plot(history.history['loss'])
plt.plot(history.history['val_loss'])
plt.title('Model loss')
plt.xlabel('Epoch')
plt.ylabel('Loss')
plt.legend(['Train', 'Validation'], loc='upper left')
plt.show()
# every training can give different results , you can mark the next line as comment when you got the best result running the test set.
model.save('ELA_CNN_ART_V2.h5')