꽃(flower) 데이터셋으로 모델을 생성하면 일정 수준의 정확도를 얻을 수 있습니다. 여기서 모델의 성능을 한층 더 최적화하고 싶다면 버퍼 프리페치(buffer prefetch)와 Rescaling 레이어를 함께 활용할 수 있습니다. 이때 Rescaling 레이어는 별도로 적용하는 것이 아니라 Keras 모델 내부에 포함시키는 방식으로 데이터셋 전체에 적용됩니다.
사용되는 데이터셋과 개발 환경
이 글에서는 수천 장의 꽃 이미지를 포함하고 있는 꽃 데이터셋을 사용합니다. 이 데이터셋은 5개의 하위 디렉터리로 구성되어 있으며, 각 하위 디렉터리는 하나의 클래스(꽃 종류)에 해당합니다.
코드 실행에는 Google Colaboratory(Colab)를 사용했습니다. Colab은 브라우저에서 바로 Python 코드를 실행할 수 있게 해주며, 별도의 환경 설정 없이 무료로 GPU(그래픽 처리 장치)를 사용할 수 있다는 장점이 있습니다. Colaboratory는 Jupyter Notebook을 기반으로 구축된 서비스입니다.
AUTOTUNE = tf.data.AUTOTUNE
train_ds = train_ds.cache().prefetch(buffer_size=AUTOTUNE)
val_ds = val_ds.cache().prefetch(buffer_size=AUTOTUNE)
num_classes = 5
print("A sequential model is built")
model = tf.keras.Sequential([
layers.experimental.preprocessing.Rescaling(1./255),
layers.Conv2D(32, 3, activation='relu'),
layers.MaxPooling2D(),
layers.Conv2D(32, 3, activation='relu'),
layers.MaxPooling2D(),
layers.Conv2D(32, 3, activation='relu'),
layers.MaxPooling2D(),
layers.Flatten(),
layers.Dense(128, activation='relu'),
layers.Dense(num_classes)
])코드 출처: https://www.tensorflow.org/tutorials/load_data/images
출력 결과
A sequential model is built
코드 설명
- 버퍼드 프리페칭(buffered prefetching)을 사용하면 I/O 작업이 블로킹(blocking)되지 않고 디스크에서 데이터를 원활하게 가져올 수 있습니다.
- 이는 데이터 로딩 과정에서 매우 중요한 단계입니다.
.cache()메서드는 첫 번째 에포크(epoch)에서 디스크로부터 이미지를 불러온 뒤 이를 메모리에 유지하는 역할을 합니다.- 덕분에 모델 학습이 진행되는 동안 데이터셋이 병목 지점이 되는 것을 방지할 수 있습니다.
- 만약 데이터셋이 메모리에 담기에는 너무 크다면, 동일한 메서드를 활용해 성능이 좋은 온디스크(on-disk) 캐시를 생성할 수도 있습니다.
.prefetch()메서드는 학습이 진행되는 동안 데이터 전처리 작업과 모델 실행 작업을 서로 겹쳐서(오버랩) 수행함으로써 전체 학습 속도를 향상시킵니다.tf.data.AUTOTUNE을 buffer_size로 지정하면 TensorFlow가 런타임 시점에 시스템 상태에 맞춰 최적의 버퍼 크기를 자동으로 조절해 줍니다.
또한 모델의 첫 번째 레이어로 배치된 Rescaling(1./255)은 픽셀 값을 0~255 범위에서 0~1 범위로 정규화(normalization)하여, 신경망이 안정적이고 빠르게 수렴하도록 돕습니다. 이처럼 전처리 레이어를 Keras 모델 안에 통합하면 데이터 파이프라인과 모델이 하나로 묶여 배포 및 재사용 측면에서도 관리가 훨씬 편리해집니다.