Нейронні мережі з якими ми працювали раніше, використовували навчальні набори даних з MNIST які вже є Keras і легко завантажуються. Тепер ми розглянемо принципи роботи із готовими зовнішніми даними, які відсутні в Кeras, або з набором даних створеним користувачем.
Робота з готовими наборами даних.
Розглянемо задачу класифікації двох типів зображень -- літаків і автомобілів. Архів з готовими даними завантажуємо звідси
Структура даних така
- Тренувальні данні ( Train data): Данні містять 200 зображень кожного автомобіля та літака, тобто всього ми маємо 400 зображень у навчальному наборі даних
- Тестові данні ( Test data): Тестові данні містять 50 зображень кожного автомобіля та літака, тобто загальна кількість їх становить 100 зображень
#Завантажуємо необхідні бібліотеки
from keras.preprocessing.image import ImageDataGenerator
from keras.models import Sequential
from keras.layers import Conv2D, MaxPooling2D
from keras.layers import Activation, Dropout, Flatten, Dense
from keras import backend as K
Задаємо параметри даних, та шлях до даних, деякі гіперпараметри мережі
img_width, img_height = 224, 224
train_data_dir = 'v_data/train'
validation_data_dir = 'v_data/test'
nb_train_samples = 400
nb_validation_samples = 100
epochs = 10
batch_size = 16
Тут, train\_data\_dir -- це каталог тренувальних даних, validation\_data\_dir -- це каталог для тестових даних, nb_train_samples -- загальна кількість тренувальних даних, nb_validation_samples -- загальна кількість тестових даних.
Задаємо формат вхідних даних в залежності від того чи RGB-канал знаходиться на першому місці чи на останньому
if K.image_data_format() == 'channels_first':
input_shape = (3, img_width, img_height)
else:
input_shape = (img_width, img_height, 3)
Визначаємо згорткову нейронну мережу та компілюємо її із стандартними параметрами компіляції. Мережа містить три згорткові шари із 32, 32, 64 карт ознак з $2 \times 2$-ядрами, за кожним з яких йде агрегуючий шар. На вхід повнозв'язної частини подається вектор довжини 64. На виході отримуємо останній шар із одного вузла.
model = Sequential()
model.add(Conv2D(32, (2, 2), input_shape = input_shape))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size =(2, 2)))
model.add(Conv2D(32, (2, 2)))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size =(2, 2)))
model.add(Conv2D(64, (2, 2)))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size =(2, 2)))
model.add(Flatten())
model.add(Dense(64))
model.add(Activation('relu'))
model.add(Dense(1))
model.add(Activation('sigmoid'))
model.compile(loss ='binary_crossentropy',
optimizer ='rmsprop',
metrics =['accuracy'])
Отримуємо мережу з такою архітектурою
Тепер підготуємо доповненні дані з нашого набору
train_datagen = ImageDataGenerator(
rescale = 1. / 255,
shear_range = 0.2,
zoom_range = 0.2,
horizontal_flip = True)
test_datagen = ImageDataGenerator(rescale = 1. / 255)
train_generator = train_datagen.flow_from_directory(train_data_dir,
target_size =(img_width, img_height),
batch_size = batch_size, class_mode ='binary') # або 'categorical' за умовчанням
validation_generator = test_datagen.flow_from_directory(
validation_data_dir,
target_size =(img_width, img_height),
batch_size = batch_size, class_mode ='binary')
Отже ImageDataGenerator поділив зображення на 255, виконав косе перетворення в деякому діапазоні, масштабував зображення і виконав горизонтальне віддзеркалення.
Функція flow_from_directory використовується для підготовки даних з вказаного каталогу і вказаного розміру зображення.
Навчання і збереження моделі
model.fit_generator(train_generator,
steps_per_epoch = nb_train_samples // batch_size,
epochs = epochs, validation_data = validation_generator,
validation_steps = nb_validation_samples // batch_size)
model.save('model_saved.h5')
Робота із моделлю
Завантажуємо модель, зображення, перетворюємо його у необхідний формат і передаємо функції model.predict(), яка повертає ймовірність належності зображення до першого класу, тобто до класу літаків.
from keras.models import load_model
import numpy as np
import cv2
model = load_model('model_saved.h5')
label=["літак", "авто"]
import cv2
tst=cv2.imread('file.jpg',1)# Завантажуємо зображення як кольорове
tst=cv2.resize(tst, (224, 224))
tst = tst.reshape( 1,224 , 224,3)
tst=tst.astype('float32') / 255
pred=list(model.predict(tst)[0])
if pred[0]>0.5: print(label[0])
else: print(label[1])
Немає коментарів:
Дописати коментар