Deep Learning - 이미지 처리 CNN 이용한 이미지 분류 모델 구현 실습 (1)
CNN을 이용한 이미지 분류
커머스 산업에 관심이 많다보니, 커머스에서 사용할 수 있는 모델을 구상해보았고, 이미지를 통한 카테고리 분류를 한다면 하루에도 수많은 상품이 업데이트되는 커머스 플랫폼에선 자동화의 일환으로 사용할 수 있을 것이다.
Cifar10 데이터를 이용한 실습
from tensorflow.keras import datasets
from tensorflow.keras.models import Sequential, Model
from tensorflow.keras.layers import Dense, Conv2D, MaxPooling2D, Flatten
(train_images, train_labels), (test_images, test_labels) = datasets.cifar10.load_data()
# Normalize pixel values to be between 0 and 1
train_images, test_images = train_images / 255.0, test_images / 255.0
# 라벨 설정
class_names = ['airplane', 'automobile', 'bird', 'cat', 'deer',
'dog', 'frog', 'horse', 'ship', 'truck']
keras 제공 cifar10 데이터를 이용하기 위해 불러온 뒤, 정규화를 위해 255로 나눠준다.
기본적으로 cifar10 데이터는 10개의 라벨로 이뤄져있어, 해당 라벨을 분류할 수 있도록 모델 설계를 해주면 된다.
import matplotlib.pyplot as plt
plt.figure(figsize=(10,10))
for i in range(25):
plt.subplot(5,5,i+1)
plt.xticks([])
plt.yticks([])
plt.grid(False)
plt.imshow(train_images[i], cmap=plt.cm.binary)
# The CIFAR labels happen to be arrays,
# which is why you need the extra index
plt.xlabel(class_names[train_labels[i][0]])
plt.show()
train데이터 5만개 중 25개만 이미지를 띄워보면 위와같이 나온다. 위의 이미지를 학습하여 test 셋의 이미지를 맞추는지 실험해보도록 한다.
model = Sequential()
model.add(Conv2D(32, 3, activation = 'relu', input_shape=(32,32,3)))
model.add(MaxPooling2D(2,2))
model.add(Conv2D(64, 3, activation = 'relu'))
model.add(MaxPooling2D(2,2))
model.add(Conv2D(64, 3, activation = 'relu'))
model.add(Flatten())
model.add(Dense(64, activation='relu'))
model.add(Dense(10, activation='softmax'))
model.summary()
- Sequential()로 model 인스턴스를 생성한다.
- Conv2D를 통해 컨볼루션 레이어를 추가한다. 필터와 노드수, 활성함수를 정한다.
뎁스 32, 필터 (3,3), 활성함수 relu, 인풋사이즈 (32,32에 3채널) - MaxPooling2D를 지정해준다. 사이즈 (2,2) > default이기도 함.
- Conv와 Pooling을 반복한 뒤, Flatten으로 이미지를 1차원으로 변형
- 이후 FC에 넣어 은닉층 하나를 거쳐 최종 softmax를 취해 10개 라벨을 분류한다.
[output]
Model: "sequential"
_________________________________________________________________
Layer (type) Output Shape Param #
=================================================================
conv2d (Conv2D) (None, 30, 30, 32) 896
max_pooling2d (MaxPooling2D (None, 15, 15, 32) 0
)
conv2d_1 (Conv2D) (None, 13, 13, 64) 18496
max_pooling2d_1 (MaxPooling (None, 6, 6, 64) 0
2D)
conv2d_2 (Conv2D) (None, 4, 4, 64) 36928
flatten (Flatten) (None, 1024) 0
dense (Dense) (None, 64) 65600
dense_1 (Dense) (None, 10) 650
=================================================================
Total params: 122,570
Trainable params: 122,570
Non-trainable params: 0
_________________________________________________________________
model.summary()를 통해 파라미터 수 변화, 인풋데이터의 shape 변화를 볼 수 있다.
위와같이 진행 후 컴파일을 해준다.
model.compile(optimizer='adam',
loss='sparse_categorical_crossentropy',
metrics=['accuracy'])
model.fit(train_images, train_labels, epochs=10, validation_data=(test_images, test_labels))
- 옵티마이저를 설정한다. adam이 가장 범용적으로 자주 사용되는 녀석
- 여러가지 분류를 진행할때 0과1이 아닌 숫자로 구분을 하기 위해선 categorical보다 sparse_categorical_crossentropy를 사용하도록 한다.
- metric은 가장 기본적인 accuracy로 지정한다.
- model fit을 진행한다.
[output]
Epoch 1/10
1563/1563 [==============================] - 11s 7ms/step - loss: 1.5798 - accuracy: 0.4221 - val_loss: 1.3096 - val_accuracy: 0.5288
Epoch 2/10
1563/1563 [==============================] - 9s 6ms/step - loss: 1.2251 - accuracy: 0.5639 - val_loss: 1.1692 - val_accuracy: 0.5920
Epoch 3/10
1563/1563 [==============================] - 10s 6ms/step - loss: 1.0634 - accuracy: 0.6261 - val_loss: 1.0515 - val_accuracy: 0.6330
Epoch 4/10
1563/1563 [==============================] - 10s 6ms/step - loss: 0.9634 - accuracy: 0.6622 - val_loss: 1.0322 - val_accuracy: 0.6387
Epoch 5/10
1563/1563 [==============================] - 10s 6ms/step - loss: 0.8922 - accuracy: 0.6886 - val_loss: 0.9355 - val_accuracy: 0.6719
Epoch 6/10
1563/1563 [==============================] - 10s 6ms/step - loss: 0.8331 - accuracy: 0.7113 - val_loss: 0.9039 - val_accuracy: 0.6864
Epoch 7/10
1563/1563 [==============================] - 9s 6ms/step - loss: 0.7868 - accuracy: 0.7243 - val_loss: 0.8952 - val_accuracy: 0.6916
Epoch 8/10
1563/1563 [==============================] - 9s 6ms/step - loss: 0.7464 - accuracy: 0.7376 - val_loss: 0.9186 - val_accuracy: 0.6839
Epoch 9/10
1563/1563 [==============================] - 9s 6ms/step - loss: 0.7063 - accuracy: 0.7518 - val_loss: 0.8898 - val_accuracy: 0.6986
Epoch 10/10
1563/1563 [==============================] - 9s 6ms/step - loss: 0.6677 - accuracy: 0.7668 - val_loss: 0.9407 - val_accuracy: 0.6927
# 수행
test_loss, test_acc = model.evaluate(test_images, test_labels, verbose=2)
[output]
313/313 - 1s - loss: 0.9407 - accuracy: 0.6927 - 913ms/epoch - 3ms/step
val_accuracy가 높게 나오진 않았지만, 레이어를 늘리거나 학습을 더 하면 좀 더 높아진다.(과적합조심)
import matplotlib.pyplot as plt
plt.figure(figsize=(10,10))
for i in range(5):
plt.subplot(5,5,i+1)
plt.xticks([])
plt.yticks([])
plt.grid(False)
plt.imshow(test_images[i], cmap=plt.cm.binary)
# The CIFAR labels happen to be arrays,
# which is why you need the extra index
plt.xlabel(class_names[test_labels[i][0]])
plt.show()
위와같이 테스트 셋의 다섯개 이미지를 분류해본다.
plt.figure(figsize=(10,10))
for i in range(5):
x = np.expand_dims(test_images[i], axis=0) # 이미지의 차원을 맞추기 위해 늘려줘야한다.
predictions = model.predict(x) # 예측을 진행한다.
predicted_ids = np.argmax(predictions, axis=-1)
predicted_class_names = class_names[predicted_ids[0]]
plt.subplot(5,5,i+1)
plt.xticks([])
plt.yticks([])
plt.grid(False)
plt.imshow(test_images[i], cmap=plt.cm.binary)
plt.title(predicted_class_names)
결과를 보면 5개 모두 화질지 좋지 않음에도 잘 맞춘것을 볼 수 있다. 이러한 방식으로 상품이미지에 대한 카테고리 라벨을 학습시켜 이미지 특징으로 카테고리를 구분할 수 있는 인공지능을 만들어 봐야겠다.
Author And Source
이 문제에 관하여(Deep Learning - 이미지 처리 CNN 이용한 이미지 분류 모델 구현 실습 (1)), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://velog.io/@dlskawns/Deep-Learning-이미지-처리-CNN-이용한-이미지-분류-모델-구현-실습-1저자 귀속: 원작자 정보가 원작자 URL에 포함되어 있으며 저작권은 원작자 소유입니다.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)