본문 바로가기
딥러닝

Keras로 간단한 CNN 구현하기

by 초특급하품 2019. 11. 13.

Keras로 가장 기본적인 mnist를 CNN(convolutional neural network)으로 구현하는 방법을 알아보자.

데이터 다운로드

(x_train, y_train), (x_test, y_test) = keras.datasets.mnist.load_data()

 

keras가 기본으로 mnist 데이터셋을 지원하기 때문에 바로 사용할 수 있다.
load_data()는 s3에 있는 mnist 파일을 다운받아 ~/.keras/datasets 폴더에 캐시 한다. 파일은 .npz 포맷으로 되어 있고, x_train, y_train, x_test, y_test 이름의 배열을 읽어서 tuple로 리턴한다.

 

데이터 전처리

x_train = x_train.reshape(x_train.shape[0], 28, 28, 1)
x_test = x_test.reshape(x_test.shape[0], 28, 28, 1)

x_train = x_train.astype('float32') / 255.
x_test = x_test.astype('float32') / 255.

y_train = keras.utils.to_categorical(y_train, 10)
y_test = keras.utils.to_categorical(y_test, 10)

 

keras의 minst 입력 데이터는 60000개의 28x28 uint8로 이루어져 있다.

>>> print(x_train.shape, x_train.dtype)
(60000, 28, 28) uint8

 

이를 기본 CNN 골격에 맞게 28x28x1로 차원을 변경하고 uint8을 float으로 바꾼다. 각 픽셀의 값은 [0, 255] 사이의 값이므로 255로 나누어 [0, 1]로 맞췄다.

keras util의 to_categorical함수로 label에 해당하는 [0, 9] 사이의 숫자 y를 바이너리 배열로 변환한다. (one-hot encoding)

 

모델 설계

model = Sequential()
model.add(Conv2D(filters=32,
                 kernel_size=(5, 5),
                 strides=(1, 1),
                 padding='same',
                 activation='relu',
                 input_shape=(28, 28, 1))
model.add(MaxPooling2D(pool_size=(2, 2),
                       strides=(2, 2)))
model.add(Conv2D(filters=64,
                 kernel_size=(3, 3),
                 strides=(1, 1),
                 activation='relu',
                 padding='same'))
model.add(MaxPooling2D(pool_size=(2, 2),
                       strides=(2, 2)))
model.add(Dropout(0.3))
model.add(Flatten())
model.add(Dense(units=500,
                activation='relu'))
model.add(Dropout(0.3))
model.add(Dense(units=10,
                activation='softmax'))

model.compile(loss='categorical_crossentropy',
              optimizer='adam',
              metrics=['accuracy'])

 

Sequantial은 layer를 순차적으로 연결하는 모델이다. .add() 명령으로 layer를 추가할 수 있다.
keras의 layerconvolutional에 이미 정의된 클래스들이 있어서 인자만 넘기면 쉽게 생성할 수 있다.

Conv2D

  • filters: 필터(커널)의 개수
  • kernel_size: 필터의 크기
  • strides: 필터의 이동 간격
  • padding: valid(패딩 없음), same(인풋과 아웃풋이 같도록 패딩)
  • activation: 활성화 함수
  • input_shape: 첫 레이어에 인풋으로 들어오는 크기

MaxPooling2D

  • pool_size: 축소시킬 필터의 크기
  • strides: 필터의 이동 간격. 기본값으로 pool_size를 갖는다.

Dropout

  • rate: 해당 비율만큼 drop 시킨다.
  • 학습용이므로 테스트 단계에서는 dropout 되지 않는다.

Flatten

  • 1차원으로 변환하는 layer

Dense

  • unit: 완전 연결(fully connected) layer로 아웃풋 개수
  • activation: 활성화 함수

compile 함수

  • loss: 손실 함수
  • optimizer: 학습 옵티마이저
  • metrics: 모델이 평가할 항목들

마지막은 10개의 리스트를 softmax로 마무리해서 각 숫자일 확률을 출력할 수 있도록 한다.

summary 명령으로 모델의 layer와 속성들을 확인할 수 있다.

>>> model.summary()
Model: "sequential_1"
_________________________________________________________________
Layer (type)                 Output Shape              Param #   
=================================================================
conv2d_1 (Conv2D)            (None, 28, 28, 32)        832       
_________________________________________________________________
max_pooling2d_1 (MaxPooling2 (None, 14, 14, 32)        0         
_________________________________________________________________
conv2d_2 (Conv2D)            (None, 14, 14, 64)        30784     
_________________________________________________________________
max_pooling2d_2 (MaxPooling2 (None, 7, 7, 64)          0         
_________________________________________________________________
dropout_1 (Dropout)          (None, 7, 7, 64)          0         
_________________________________________________________________
flatten_1 (Flatten)          (None, 3136)              0         
_________________________________________________________________
dense_1 (Dense)              (None, 500)               1568500   
_________________________________________________________________
dropout_2 (Dropout)          (None, 500)               0         
_________________________________________________________________
dense_2 (Dense)              (None, 10)                5010      
=================================================================
Total params: 1,605,126
Trainable params: 1,605,126
Non-trainable params: 0
_________________________________________________________________

 

학습

history = model.fit(x=x_train,
                    y=y_train,
                    batch_size=100,
                    epochs=15,
                    verbose=1,
                    validation_data=(x_test, y_test))

 

여러 layer를 쌓아 만든 model을 학습시킵니다.

  • epochs: 입력 데이터 학습 횟수
  • batch_size: 학습할 때 사용되는 데이터 수
  • validation_data: 검증 데이터로 하나의 epoch가 끝날 때마다 모델을 평가해줌
  • verbose: 학습 중 출력되는 로그 수준 (0, 1, 2)

 

평가

score = model.evaluate(x_test, y_test, verbose=0)

 

학습시킨 모델로 실제 테스트를 평가해보면 loss와 accuracy를 구할 수 있다.

'딥러닝' 카테고리의 다른 글

Keras로 CartPole 강화학습  (0) 2019.12.08
Keras로 모델 저장, 불러오기  (0) 2019.11.16
알파고의 몬테카를로 방법  (0) 2019.11.10
알파고의 강화학습  (0) 2019.11.03
강화학습의 종류  (0) 2019.11.03

댓글