데이터 증강(Data Augmentation)이해
CNN 모델의 성능을 높이고 오버피팅을 극복할 수 있는 가장 좋은 방법은 다양한 유형의 학습 이미지 데이터 양을 늘리는 것입니다. 하지만 이미지 데이터의 경우 학습 데이터 량을 늘리는 것은 쉽지가 않습니다. 데이터 증강(Data Augmentation)은 학습 이미지의 개수를 늘리는 것이 아니고 학습 시 마다 개별 원본 이미지를 변형해서 학습하는 것입니다.
ImageDataGenerator(Keras)
import cv2
import matplotlib.pyplot as plt
from tensorflow.keras.preprocessing.image import ImageDataGenerator
#cv2.imread는 이미지를 RGB가 아닌 BGR로 받아오기 때문에 바꿔 주어야함.
image = cv2.cvtColor(cv2.imread('test.jpg'), cv2.COLOR_BGR2RGB)
plt.imshow(image)
#augmentation이 적용된 image들을 시각화 해주는 함수
def show_aug_image(image, generator, n_images=4):
# ImageDataGenerator는 여러개의 image를 입력으로 받기 때문에 4차원으로 입력 해야함.
image_batch = np.expand_dims(image, axis=0)
# featurewise_center or featurewise_std_normalization or zca_whitening 가 True일때만 fit 해주어야함
generator.fit(image_batch)
# flow로 image batch를 generator에 넣어주어야함.
data_gen_iter = generator.flow(image_batch)
fig, axs = plt.subplots(nrows=1, ncols=n_images, figsize=(24, 8))
for i in range(n_images):
#generator에 batch size 만큼 augmentation 적용(매번 적용이 다름)
aug_image_batch = next(data_gen_iter)
aug_image = np.squeeze(aug_image_batch)
aug_image = aug_image.astype('int')
axs[i].imshow(aug_image)
data_generator = ImageDataGenerator(horizontal_flip=True)
show_aug_image(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(vertical_flip=True)
show_aug_image(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(horizontal_flip=True, vertical_flip=True)
show_aug_image(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(rotation_range=45)
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(width_shift_range=0.4, fill_mode='nearest')
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(width_shift_range=0.4, fill_mode='reflect')
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(width_shift_range=0.4, fill_mode='wrap')
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(width_shift_range=0.4, fill_mode='constant', cval=0)
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(shear_range=45)
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(zoom_range=[0.5, 0.9])
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(zoom_range=[1.1, 1.5], fill_mode='constant', cval=0)
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(brightness_range=(0.1, 0.9))
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(brightness_range=(1.0, 1.0))
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(brightness_range=(1.0, 2.0))
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(channel_shift_range=150)
show_aug_image_batch(image, data_generator, n_images=4)
data_generator = ImageDataGenerator(
rotation_range=20,
width_shift_range=0.2,
height_shift_range=0.2,
brightness_range=(0.7, 1.3),
horizontal_flip=True,
vertical_flip=True,
#rescale=1/255.0 # 학습시 적용, 시각화를 위해 임시로 주석처리
)
show_aug_image_batch(image, data_generator, n_images=4)
위의 그림들을 보면 적용이 된 그림도 있고 되지 않은 그림도 있습니다. 아무것도 적용이 되지 않은 그림은 원본 이미지와 같습니다. 그렇다고 이것이 나쁜것만은 아닙니다. 데이터를 학습할때 원본의 이미지가 하나도 없으면 학습이 잘 되지 않습니다. 위와 같이 keras의 ImageDataGenerator는 확률이 랜덤하게 적용됩니다.
위의 그림을 보면 Augmentation 적용후 빈공간이 있습니다. 이 빈공간을 어떻게 채울지 결정해 주어야 합니다. fill_node의 파라미터로 입력을 받으며 디폴트는 nearest 입니다.
- nearest: 주변 환경 그대로 가져옴
- reflect: 거울 모드로 가져옴
- wrap: 잘린 부분을 채움
- constant: cval 파라미터 값으로 채움 (0 ~ 255, 0에 가까울수록 어두워진다.)
ImageDataGenerator 변환 유형
Flip
- 좌우 반전: horizontal_flip = True
- 상하 반전: vertical_flip = True
Rotation
- rotation_range = x
- 임의의 -x ~ +x 사이 회전
- 빈 공간은 fill_mode로 채워짐, default는 nearest
Zoom
- zoom_range = [0.5, 1.5]
- 1보다 작은 값은 확장
- 1보다 큰 값은 축소(빈 공간은 fill_mode로 채워짐, default는 nearest)
Shift
- 좌우 이동: width_shift_range = 0.2
- 상하 이동: height_shift_range = 0.2
- 0~1사이 값
- 빈 공간은 fill_mode로 채워짐, default는 nearest
Shear
- shear_range = 45
- X축 또는 y축 중심으로 0~45도 사이 변환
Bright
- brightness_range = (0.1, 0.9)
- 밝기 조절, 0~1사이 값 입력, 0에 가까울수록 어둡고, 1에 가까울수록 밝음
Channel Shift
- channel_shift_range = x
- R, G, B Pixel값을 -x ~ x 사이의 임의의 값을 더하여 변환, 0보다 작으면 0, 255보다 크면 255로 초기화
Normalization
- featurewise_center=True, 각 R, G, B Pixel 값에서 개별 채널 별 평균 Pixel값을 빼서 평균이 0이 되게 유지
- featurewise_std_normalization=True 각 R, G, B Pixel값에서 개별 채널 별 표준 편차 Pixel값을 나눈다.
- rescale = 1/255.0. 딥러닝은 입력이 비교적 작은 값을 선호하므로 0~255 -> 0~1
'컴퓨터비전 > CNN' 카테고리의 다른 글
[딥러닝] Kears의 전처리와 데이터 로딩의 이해 (0) | 2022.03.16 |
---|---|
[딥러닝] 전이 학습(Transfer Learning) (0) | 2022.03.15 |
[딥러닝] GAP(Global Average Pooling) (0) | 2022.03.14 |
[딥러닝] 배치 정규화(Batch Normalization) (0) | 2022.03.13 |
[딥러닝] CNN(Convolutional Neural Network)의 이해 (1) | 2022.03.11 |
댓글