딥러닝

딥러닝(18) Transfer Learning과 Fine Tunning

개발연습자1 2023. 1. 3. 13:04

Transfer Learning은 기존의 잘설계된 모델에 자신의 모델을 덧붙여 딥러닝을 진행하는 방법으로 회사에서도 많이 쓰이는 방법이다. Fine Tunning은 글 뒤에 후술하겠지만 Transfer Learning을 진행한 학습 모델에서 레이어를 다듬어 다시 학습하는 방법이다.

 

우선 Transfer Learning을 진행해보자

 

우선 데이터 파일을 받는다.

!wget --no-check-certificate \
    https://storage.googleapis.com/mledu-datasets/cats_and_dogs_filtered.zip \
    -O ./cats_and_dogs_filtered.zip

 

라이브러리를 호출한다.

import os
import zipfile
import numpy as np
import tensorflow as tf
import matplotlib.pyplot as plt

# 파이썬의 진행상태를 표시해 주는 라이브러리
from tqdm import tqdm_notebook

from tensorflow.keras.preprocessing.image import ImageDataGenerator

%matplotlib inline
tf.__version__

 

데이터의 압축을 풀고 지정한 디렉토리에 저장한다.

file = zipfile.ZipFile('/content/cats_and_dogs_filtered.zip')

file.extractall('./')

 

train과 test 데이터의 디렉토리 경로를 설정한다.

train_dir='/content/cats_and_dogs_filtered/train'

test_dir='/content/cats_and_dogs_filtered/validation'

 

이미지 인풋 사이즈는 (128,128,3)으로 설정한다.

IMG_SHAPE = (128, 128, 3)

 

트랜스퍼 러닝에 활용할 잘만들어진 모델을 가져온다. 필자는MobileNetV2를 쓰기로 하였다.

base_model = tf.keras.applications.MobileNetV2(input_shape=IMG_SHAPE,include_top=False)

 

모델의 요약을 찍어보면 레이어가 많은 것을 알수 있다. 

base_model.summary()

 

트랜스퍼러닝에 활용할 우리의 모델을 만든다.

import tensorflow as tf
from keras.layers import Dense, Flatten, Conv2D, MaxPool2D
from keras.models import Sequential

head_model = base_model.output
head_model = Flatten()(head_model)
head_model = Dense(128,'relu')(head_model)
head_model = Dense(1,'sigmoid')(head_model)

 

앞에 쓰는 베이스 모델은 학습을 하지 않고 레이어만 쓴다.

base_model.trainable = False

 

잘만들어진 베이스모델과 우리의 헤드모델을 이어 붙인다.

from keras.models import Model
model = Model(inputs = base_model.input,outputs = head_model)

 

트랜스퍼러닝의 모델에서는 베이스모델은 학습하지 않는다. 요약을 통해 확인 할수 있다.

model.summary()

 

학습 안하는 레이어 숫자가 많이 늘었다.

 

합쳐진 모델을 컴파일 한다.

from keras.optimizers import RMSprop

model.compile(RMSprop(0.0001), loss='binary_crossentropy', metrics=['accuracy'])

 

이미지 제너레이터로 이미지 데이터를 증강시킨다.

train_datagen = ImageDataGenerator(rescale = 1/255.0,rotation_range=30,
                                   width_shift_range= 0.4,
                                   height_shift_range= 0.2,
                                   shear_range=0.3,
                                   zoom_range=0.5,
                                   horizontal_flip=True)
                                   
test_datagen = ImageDataGenerator(rescale = 1/255.0)

train_generator=train_datagen.flow_from_directory(train_dir, target_size=(128,128), class_mode='binary',batch_size=128)
test_generator=test_datagen.flow_from_directory(test_dir, target_size=(128,128), class_mode='binary',batch_size=128)

 

학습을 진행한다.

epoch_history = model.fit(train_generator,epochs=5,
                          validation_data=(test_generator))

 

모델을 평가한다.

model.evaluate(test_generator)

 

이제 학습이 완료되었으니 Fine Tunning을 진행한다.

 

Fine Tunning은 학습을 진행하지 않은 베이스 모델의 레이어중 일부를 써서 Transfer Learning을 다시 학습하는 방법이다.

 

Fine Tunning을 하려면  Transfer Learning이 반드시 학습된 상태여야 한다.

 

일단은 베이스 모델의 전체 레이어를 다시, 학습 가능하도록 한다.
base_model.trainable = True
 
베이스 모델의 전체 레이어 수를 확인하고 어디까지 레이어를 학습할것인지 정해준다.
#전체 레이어수 확인
len(base_model.layers)

#학습할 레이어수를 정한다.
end_layer = 100

 

학습할 레이어수까지만 남겨두고 나머지 레이어는 비학습화한다.

for layer in base_model.layers[0:end_layer+1]:
  layer.trainable = False

 

다시 모델을 컴파일 한다.

from keras.optimizers import Adam
model.compile(Adam(0.0001), loss='binary_crossentropy', metrics=['accuracy'])

 

모델을 학습한다.

epoch_history2 = model.fit(train_generator,epochs=5,
                          validation_data=(test_generator))

 

모델을 평가한다.

model.evaluate(test_generator)
반응형