สรุปขั้นตอน
- Prepare train data
- Read train csv
- [x] Load image
- [x] Convert image to array
- [x] Put image array in list
- [x] Convert list to numpy array
- [y] Transform label in form of 0 to n-1
- [y] Convert list to one-hot array
- Pre-process image
- Split train and validation data
- Data augmentation
- Build a model
- Create model and summary
- Complile model
- Train data with model
- Show train result
- Save model
- Save history
- Show time used
- Plot train accuracy and loss
- Prepare test data
- Read test csv
- [x] Load image
- [x] Convert image to array.
- [x] Put image array in list
- [x] Convert list to numpy array
- [x] Normalized array
- [y] Transform label to list 0 to n-1
- [y] Convert list to numpy array
- [y] Convert list to one-hot array
- Predict test data
- Show test result
- Evaluate model
- Convert one-hot to list
- Save prediction
- Plot confusion matrix
- Print and save classification report
1. Prepare train data
1.1 Read train csv
import pandas as pd
rcsv = pd.read_csv('train.csv', dtype={'image': 'object', 'category': 'int8'})
rcsv.head()
การเรียก column เป็น list
a = trainCsv.iloc[:, :-1].values
b = trainCsv.iloc[:, 1].values
c = trainCsv.image
d = trainCsv.category
e = trainCsv['image'].values
f = trainCsv['category'].values
1.2 [x] Load image
from keras.preprocessing.image import load_img
imgPath = 'train/2556711.jpg'
imgDim = (150, 150)
img1 = load_img(imgPath, target_size=imgDim)
1.3 [x] Convert image to array
from keras.preprocessing.image import img_to_array, array_to_img
imgToArr1 = img_to_array(img1)
arrToImg1 = array_to_img(imgToArr1)
1.4 [x] Put image array in list
imgDim = (224,224)
trainArrListX = []
for imgName in trainCsv.image:
trainArrListX.append(img_to_array(load_img('train/'+imgName, target_size=imgDim)))
หรือเขียนแบบสั้นๆ ดังนี้
trainArrListX = [img_to_array(load_img('train/'+img_name, target_size=imgDim)) for imgName in trainCsv.image]
1.5 [x] Convert list to numpy array
import numpy as np
x_train = np.array(trainArrListX)
1.6 [y] Transform label in form of 0 to n-1
1.7 [y] Convert list to one-hot array
ตัวเลขใน label ต้องเริ่มจาก 0 จึงจะมาแปลงเป็น to_categorical ได้ จึงต้องลบ 1 เพราะ label เดิมคือ 1, 2, 3, 4, 5trainY = trainCsv['category'].values
trainY = trainY - 1
from keras.utils import to_categorical
y_train_onehot = to_categorical(trainY)
2. Pre-process image
2.1 Split train and validation data
from sklearn.model_selection import train_test_split
x_train, x_val, y_train, y_val = train_test_split(x_train, y_train_onehot, test_size=0.2, random_state=42)
2.2 Data augmentation
การกำหนดค่า augmentation และ rescale ด้วย ImageDataGeneratorfrom keras.preprocessing.image import ImageDataGenerator
batch_size = 32
#Create the augmentation configuration
train_datagen = ImageDataGenerator(rescale=1./255,
rotation_range=30,
width_shift_range=0.2,
height_shift_range=0.2,
shear_range=0.2,
zoom_range=0.2,
brightness_range=[0.5,1],
horizontal_flip=True,)
val_datagen = ImageDataGenerator(rescale=1./255)
#Create the image generators
train_generator = train_datagen.flow(x_train, y_train, batch_size=batch_size)
val_generator = val_datagen.flow(x_val, y_val, batch_size=batch_size)
หรือใส่ชนิดค่าและการ rescale เอง (manually)
x_train = x_train.astype('float32')
x_train /= 255
ดูตัวอย่างรูปที่ทำ augmentation
import matplotlib.pyplot as plt
%matplotlib inline
plt.figure(figsize=(24,10))
x,y = train_generator.next()
for i in range(1,11):
image = x[i]
plt.subplot(2,5,i)
plt.imshow(image)
3. Build a Model
3.1 Create model and summary
from tensorflow.keras import Sequential
from tensorflow.keras.layers import Dense, GlobalAveragePooling2D
from tensorflow.keras.applications import MobileNet
IMG_SHAPE = (200, 200, 3)
base_model = MobileNet(weights='imagenet', include_top=False, input_shape=IMG_SHAPE)
base_model.trainable = False
model = Sequential([
base_model,
GlobalAveragePooling2D(),
Dense(1024,activation='relu'),
Dense(512,activation='relu'),
Dense(5, activation='softmax')
])
model.summary()
3.2 Complile model
model.compile(loss='categorical_crossentropy',optimizer='Adam',metrics=['accuracy'])
4. Train data with model
batch_size = 32
import time
startTime = time.time()
history = model.fit_generator(train_generator,
steps_per_epoch=len(x_train) // batch_size,
epochs=10)
endTime = time.time()
5. Show train result
5.1 Save model
model.save_weights('my-model_save-wieghts.h5')
model.save('my-model_save.h5')
5.2 Save history
histDf = pd.DataFrame(history.history)
histCsv = 'my-model_history.csv'
with open(histCsv, mode='w') as f:
histDf.to_csv(f)
5.3 Show time used
print("Strat time = "+str(startTime))
print("End time = "+str(endTime))
print("Use time = "+str(endTime-startTime))
5.4 Plot train accuracy and loss
import matplotlib.pyplot as plt
%matplotlib inline
acc = history.history['acc']
loss = history.history['loss']
epochs = range(1, len(acc) + 1)
#Train and validation accuracy
plt.style.use('default')
plt.grid(True)
plt.xticks(np.arange(0, len(acc)+1, 1.0))
#plt.yticks(np.arange(0, 1))
plt.plot(epochs, acc, 'b', label='Training Accurarcy')
plt.title('Training Accuracy (My Model)')
plt.legend()
plt.grid(True)
plt.figure()
plt.plot(epochs, loss, 'r', label='Training Loss')
plt.grid(True)
plt.xticks(np.arange(0, len(acc)+1, 1.0))
plt.title('Training Loss (My Model)')
plt.legend()
plt.show()
6. Prepare test data
6.1 Read test csv
6.2 [x] Load image
6.3 [x] Convert image to array.
6.4 [x] Put image array in list
6.5 [x] Convert list to numpy array
6.6 [x] Normalized array
testCsv = pd.read_csv('test.csv', dtype={'image': 'object', 'category': 'int8'})
testArrListX = [img_to_array(load_img('test/'+imgName, target_size=imgDim)) for imgName in testCsv.image]
x_test = np.array(testArrListX)/255.0
6.7 [y] Convert list to numpy array
6.8 [y] Convert list to one-hot array
testY = testCsv['category'].values
testY = testY - 1
y_test = np.array(testY)
y_test_onehot = to_categorical(testY)
7. Predict test data
y_pred_onehot = model.predict(x_test)
8. Show test result
8.1 Evaluate model
y_pred_onehot = model.predict(x_test)
- 16s 33ms/sample - loss: 0.2866 - accuracy: 0.9020 0.3295358799695969 0.902
8.2 Convert one-hot to list
y_pred = []
for i in range(len(y_pred_onehot)):
y_pred.append(np.argmax(y_pred_onehot[i]))
หรือ
y_pred = [np.argmax(y_pred_onehot[i]) for i in range(len(y_pred_onehot))]
8.3 Save prediction
testDict = {'image': testCsv.image, 'y_true': testCsv.category-1, 'y_pred': y_pred}
dfPred = pd.DataFrame(testDict)
exportPred = dfPred.to_csv(r'prediction.csv', index = None, header=True)
8.4 Plot confusion matrix
from sklearn.metrics import confusion_matrix
cfArr = confusion_matrix(y_test, y_pred)
import seaborn as sn
dfCm = pd.DataFrame(cfArr, index = ['Cargo', 'Military', 'Carrier', 'Cruise', 'Tankers'], columns = ['Cargo', 'Military', 'Carrier', 'Cruise', 'Tankers'])
plt.figure()
sn.heatmap(dfCm, annot=True, cmap="Blues")
plt.title('Confusion Matrix (My Model)',fontsize = 15)
plt.show()
8.5 Print and save classification report
from sklearn.metrics import classification_report
print(classification_report(y_test, y_pred))
report = classification_report(y_test, y_pred, output_dict=True)
dfRp = pd.DataFrame(report).transpose()
exportRp = dfRp.to_csv(r'classification-report.csv', index = None, header=True)
โค้ดเต็ม
# ---------- 1. Prepare train data ----------
import numpy as np
rcsv = pd.read_csv('train.csv', dtype={'image': 'object', 'category': 'int8'})
trainArrListX = [img_to_array(load_img('train/'+img_name, target_size=(200,200))) for imgName in trainCsv.image]
x_train = np.array(trainArrListX)
from keras.utils import to_categorical
trainY = trainCsv['category'].values
trainY = trainY - 1
y_train_onehot = to_categorical(trainY)
# ---------- 2. Pre-process image ----------
from sklearn.model_selection import train_test_split
x_train, x_val, y_train, y_val = train_test_split(x_train, y_train_onehot, test_size=0.2, random_state=42)
from keras.preprocessing.image import ImageDataGenerator
batch_size = 32
train_datagen = ImageDataGenerator(rescale=1./255,
rotation_range=30,
width_shift_range=0.2,
height_shift_range=0.2,
shear_range=0.2,
zoom_range=0.2,
brightness_range=[0.5,1],
horizontal_flip=True,)
val_datagen = ImageDataGenerator(rescale=1./255)
train_generator = train_datagen.flow(x_train, y_train, batch_size=batch_size)
val_generator = val_datagen.flow(x_val, y_val, batch_size=batch_size)
# ---------- 3. Build a model ----------
from tensorflow.keras import Sequential
from tensorflow.keras.layers import Dense, GlobalAveragePooling2D
from tensorflow.keras.applications import MobileNet
IMG_SHAPE = (200, 200, 3)
base_model = MobileNet(weights='imagenet', include_top=False, input_shape=IMG_SHAPE)
base_model.trainable = False
model = Sequential([
base_model,
GlobalAveragePooling2D(),
Dense(1024,activation='relu'),
Dense(512,activation='relu'),
Dense(5, activation='softmax')
])
model.summary()
model.compile(loss='categorical_crossentropy',optimizer='Adam',metrics=['accuracy'])
# ---------- 4. Train data with model ----------
import time
batch_size = 32
startTime = time.time()
history = model.fit_generator(train_generator,
steps_per_epoch=len(x_train) // batch_size,
epochs=10)
endTime = time.time()
# ---------- 5. Show train result ----------
# ---- Save model & history, Show time used ----
model.save_weights('my-model_save-wieghts.h5')
model.save('my-model_save.h5')
import pandas as pd
histDf = pd.DataFrame(history.history)
histCsv = 'my-model_history.csv'
with open(histCsv, mode='w') as f:
histDf.to_csv(f)
print("Strat time = "+str(startTime))
print("End time = "+str(endTime))
print("Use time = "+str(endTime-startTime))
# ---- Plot train accuracy and loss ----
import numpy as np
import matplotlib.pyplot as plt
%matplotlib inline
acc = history.history['accuracy']
loss = history.history['loss']
epochs = range(1, len(acc) + 1)
#Train and validation accuracy
plt.style.use('default')
plt.grid(True)
plt.xticks(np.arange(0, len(acc)+1, 1.0))
plt.plot(epochs, acc, 'b', label='Training Accurarcy')
plt.title('Training Accuracy (My Model)')
plt.xlabel("Epoch #")
plt.ylabel("Accuracy")
plt.legend()
plt.grid(True)
plt.figure()
plt.plot(epochs, loss, 'r', label='Training Loss')
plt.grid(True)
plt.xticks(np.arange(0, len(acc)+1, 1.0))
plt.title('Training Loss (My Model)')
plt.xlabel("Epoch #")
plt.ylabel("Loss")
plt.legend()
plt.show()
# ---------- 6. Prepare test data ----------
import pandas as pd
testCsv = pd.read_csv('test.csv', dtype={'image': 'object', 'category': 'int8'})
testArrListX = [img_to_array(load_img('test/'+imgName, target_size=imgDim)) for imgName in testCsv.image]
x_test = np.array(testArrListX)/255.0
testY = testCsv['category'].values
testY = testY - 1
y_test = np.array(testY)
y_test_onehot = to_categorical(testY)
# ---------- 7. Predict test data ----------
y_pred_onehot = model.predict(x_test)
# ---------- 8. Show test result ----------
# ---- Evaluate model ----
model.evaluate(x_test, y_test_onehot)
# ---- Convert one-hot to list ----
y_pred = [np.argmax(y_pred_onehot[i]) for i in range(len(y_pred_onehot))]
# ---- Save prediction ----
testDict = {'image': testCsv.image, 'y_label': testY, 'y_true': testY_le, 'y_pred': y_pred}
dfPred = pd.DataFrame(testDict)
exportPred = dfPred.to_csv(r'prediction.csv', index = None, header=True)
# ---- Plot confusion matrix ----
from sklearn.metrics import confusion_matrix
cfArr = confusion_matrix(y_test, y_pred)
import seaborn as sn
dfCm = pd.DataFrame(cfArr, index = ['Cargo', 'Military', 'Carrier', 'Cruise', 'Tankers'], columns = ['Cargo', 'Military', 'Carrier', 'Cruise', 'Tankers'])
plt.figure()
sn.heatmap(dfCm, annot=True, cmap="Blues")
plt.title('Confusion Matrix (My Model)',fontsize = 15)
plt.show()
# ---- Print and save classification report ----
from sklearn.metrics import classification_report
print(classification_report(y_test, y_pred))
report = classification_report(y_test, y_pred, output_dict=True)
dfRp = pd.DataFrame(report).transpose()
exportRp = dfRp.to_csv(r'classification-report.csv', index = None, header=True)
โค้ดย่อ
import numpy as np
import pandas as pd
import time
from keras.utils import to_categorical
from sklearn.model_selection import train_test_split
from keras.preprocessing.image import ImageDataGenerator
from tensorflow.keras import Sequential
from tensorflow.keras.layers import Dense, GlobalAveragePooling2D
from tensorflow.keras.applications import MobileNet
from sklearn.metrics import classification_report
rcsv = pd.read_csv('train.csv', dtype={'image': 'object', 'category': 'int8'})
trainArrListX = [img_to_array(load_img('train/'+img_name, target_size=(200,200))) for imgName in trainCsv.image]
x_train = np.array(trainArrListX)
trainY = trainCsv['category'].values
trainY = trainY - 1
y_train_onehot = to_categorical(trainY)
x_train, x_val, y_train, y_val = train_test_split(x_train, y_train_onehot, test_size=0.2, random_state=42)
batch_size = 32
train_datagen = ImageDataGenerator(rescale=1./255,
rotation_range=30,
width_shift_range=0.2,
height_shift_range=0.2,
shear_range=0.2,
zoom_range=0.2,
brightness_range=[0.5,1],
horizontal_flip=True,)
val_datagen = ImageDataGenerator(rescale=1./255)
train_generator = train_datagen.flow(x_train, y_train, batch_size=batch_size)
val_generator = val_datagen.flow(x_val, y_val, batch_size=batch_size)
base_model = MobileNet(weights='imagenet', include_top=False, input_shape=(200,200,3))
base_model.trainable = False
model = Sequential([
base_model,
GlobalAveragePooling2D(),
Dense(1024,activation='relu'),
Dense(512,activation='relu'),
Dense(5, activation='softmax')
])
model.summary()
model.compile(loss='categorical_crossentropy',optimizer='Adam',metrics=['accuracy'])
history = model.fit_generator(train_generator,
steps_per_epoch=len(x_train) // batch_size,
epochs=10)
testCsv = pd.read_csv('test.csv', dtype={'image': 'object', 'category': 'int8'})
testArrListX = [img_to_array(load_img('test/'+imgName, target_size=(200,200))) for imgName in testCsv.image]
x_test = np.array(testArrListX)/255.0
testY = testCsv['category'].values
testY = testY - 1
y_test = np.array(testY)
y_test_onehot = to_categorical(testY)
model.evaluate(x_test, y_test_onehot)
y_pred_onehot = model.predict(x_test)
y_pred = [np.argmax(y_pred_onehot[i]) for i in range(len(y_pred_onehot))]
confusion_matrix(y_test, y_pred)
print(classification_report(y_test, y_pred))
Sign up here with your email
ConversionConversion EmoticonEmoticon