이번 포스팅은 YOLO9000: Better, Faster, Stronger (YOLO v2)에 대한 논문을 리뷰하도록 하겠습니다.
전에 정리한 적이 있는데, 발표를 해야하는 상황이 왔었는데 죄다 까먹어서... 다시 정리하는 겸 복습해보려고 합니다.
아래에는 YOLO 9000의 구현체와 이해를 더 도울 수 있는 참고 영상을 첨부합니다.
구현체(Implementation)
논문 리뷰 참고 영상
PR-23 :: YOLO 9000: Better, Faster, Stronger
1. Introduction
- Object Detection 데이터 셋들은 Classification 등의 데이터 셋과 비교하면 너무 제한적이다. 일반적으로 detection을 위한 dataset은 수십 ~ 수백개의 클래스를 포함한 수천~수십만개의 이미지를 포함하고 있는데, Classification을 위한 데이터셋은 수십만개의 클래스를 포함한 이미지가 수백만개가 있다.
- YOLO 9000 논문의 핵심은 Classification 수준의 스케일을 detection을 해보고 싶은데 detection 데이터를 직접 레이블링 치기에는 너무 힘들고 하니 수 많은 Classification 데이터를 이용해서 현재 detection 시스템에 적용해보는 방법인 hierarchical view of object classification을 제안하고, 이를 학습시키는 joint training algorithm을 제안한다.
2. Better
2-1. Batch Normalization
2-2. High Resolution Classifier
대부분의 state-of--the-art detection 방법들은 ImageNet 데이터에서 학습시킨 pre-trained classifier를 사용하는데, 대부분의 classifier의 입력이 256x256보다 작습니다. 기존의 YOLO는 detection 시스템은 입력이 244 x 244인 classifier pre-train 모델로 사용하면서 입력 사이즈를 448 x 448로 증가시켜서 object detection model을 학습시켰습니다. 하지만 YOLO v2의 경우에는 기존의 224x224의 pre-train model을 입력 사이즈를 448x448로 증가시키고 ImageNet에서 10 epoch동안 학습을 더 하고, detection학습을 진행했다고 합니다. 이를 통해서 4%의 mAP 향상을 봤다고 합니다.
2-3. Convolutional With Anchor Boxes
기존 YOLO는 bounding boxe들을 직접 regression해서 사용했는데, Anchor Box를 사용해서 box의 offset만 예측하면 regression문제가 조금 더 간단하게 풀린다고 합니다. 먼저 fully connected layer를 빼고, Pooling Layer 하나를 빼서, Convolution Layer의 해상도를 늘렸다고 합니다. 그리고 기존의 448x448 입력 크기를 416x416로 변경했는데, 이렇게 되면, 최종 feature map에서 width 및 height가 홀수가 되서, 가운데 cell이 존재할 수 있게 됩니다. 이렇게 만든 이유는 일반적으로 큰 image들은 정 가운데 cell에 들어가는 경우가 많은데, feature map이 짝수일 경우에 center 근방의 cell 4개가 이러한 큰 object를 예측하게 되는데, 이렇게 사용하는 것 보다 feature map이 홀수 width, height로 떨어져서 single cell이 생길 경우 성능이 더 좋아진다고 합니다. YOLOv2는 downsample factor가 32고, 최종 feature map의 크기는 13x13이 되게 됩니다.
기본 YOLO에서는 {objectness, x1, y1, w1, h1, x2, y2, w2, h2, C1 ... Cn} 형태의 출력 벡터가 나왔다면, YOLO v2에서는 Anchor box의 갯수만큼 클래스와 객체가 있는지에 대한 여부를 예측한다고 합니다. 예를들어 Anchor가 3개라면 출력 벡터가 [{objectness, x_offset, y_offset, w_offset, h_offset, C1 ... Cn}, {objectness, x_offset, y_offset, w_offset, h_offset, C1 ... Cn}, {objectness, x_offset, y_offset, w_offset, h_offset, C1 ... Cn}] 형태가 된다는 의미입니다. Objectness의 경우 기존 YOLO와 같이 GT와 제안된 박스의 IOU 그리고 class prediction score와 objectness score와의 condition probability로 표현 될 수 있습니다.
Anchor Box를 사용하는 경우 accuracy가 살짝 떨어지지만 기존의 YOLO가 입력 이미지 당 98개 box를 예측하는게 한계였다면, Anchor Box 적용 후에는 천개 이상으로 box를 예측할 수 있습니다. Anchor Box를 적용하지 않을 경우 mAP가 69.5에 81%의 recall을 기록했지만, Anchor Box 적용 후에는 69.2%의 mAP와 88%의 recall을 얻을 수 있었습니다. mAP가 감소했지만 recall이 증가했으므로 모델의 개선 여지가 있는 것으로 의미한다고 받아들인듯 합니다.
2-4. Dimension Clusters
일반적으로 kmeans에서의 군집화 성능은 cluster가 몇개인지에 대한 파라미터 K값에 크게 좌지우지하게 되는데, 논문에서는 이를 실험적으로 확인해서 k=5로 설정해주게 됩니다. 아무래도 k값이 적으면 연산 속도는 올라가지만 Anchor Box 후보군이 제한적이어서 Detection 성능이 떨어지고, K값을 계속해서 늘리면 성능은 좋아지지만 연산 속도에 대한 trade off관계가 있다고 합니다. 그렇다고 K를 무작정 늘린다고 성능이 한없이 좋아지는거는 아니고 어느정도 이상 K값이 증가하면 Detection 성능증가가 포화상태에 다다릅니다.
아래의 표는 유클리디언 거리와 논문에서 제안하는 방식의 거리함수를 썼을 때, 그리고 kmeans의 클러스터 갯수 파라미터 K값을 변화했을 때, Detection 성능이 어떻게 변화는지에 대한 실험 결과입니다.
2-5. Direct location prediction
Anchor Box를 사용하게 됬을 때, 발생하는 2번째 문제는 모델의 불안정성입니다. 대부분의 불안정성은 box의 (x,y) 좌표를 예측하는데서 일어나는데, region proposal 계열의 네트워크들은 값들을 이용해서값들을 다음과 같이 계산하게 됩니다.
예를들면, 값이 양수라면 Box를 오른쪽으로, 음수라면 박스를 왼쪽으로 움직이게(Shift) 합니다. 이러한 식은 제한이 없기 때문에, box가 어느쪽으로나 이동이 가능해지게 되고, 안정적인 offset값을 학습하는데 꽤 많은 시간이 걸립니다. YOLO 9000에서는 이러한 제한없는 방식을 쓰기보다는 offset의 값을 [0, 1]의 범위에서 제한을 주고 이러한 제한주는 방식을 logistic activation을 사용해서 해결합니다. 네트워크는 각 셀마다 총 5개의 bounding box값을 예측하고, 각 bounding box의 요소들은 로 구성되어있습니다.
따라서 최종 objectness와 box에 대한 요소는 다음과 같이 구할 수 있습니다.
여기서 는 해당 grid cell의 왼쪽 상단 좌표를 이야기하고, 값은 anchor box의 사전 width, height값을 의미합니다.
이렇게 사용했을 때, 네트워크는 조금 더 안정적으로 변하고 dimension cluster와 direct location prediction을 사용했을 때, 기존 YOLO에 5% 이상의 향상이 일어난다고 합니다.
2-6. Fine-Grained Features
기존의 Faster R-CNN이나 SSD는 네트워크가 가지고있는 다양한 해상도의 feature map을 proposal networks를 돌려서 얻었는데, YOLO9000은 Final Feature map의 size를 13x13으로 변경하고, 이전 layer에서 26x26의 해상도를 갖는 feature map을 passthrough layer를 이용해서 가지고와서 저해상도 feature map과 concatenates하게 되는데, 이때 공간을 맞춰서 concatenate하는게 아니라 다른 채널에 stacking하게됩니다. 이러한 방식이 ResNet의 ID Mapping과 유사한 방식이라고 이갸합니다. 방법은 26x26x512의 feature map을 13x13x2048 feature map에 stacking하게됩니다. 이런 형태로 고해상도의 feature map을 가져와서 쓰게 되면 1%의 성능향상이 일어나게 된다고 합니다.
2-7. Multi-Scale Training
기존 YOLO에서 사용하던 입력크기를 448x448를 416x416으로 변경하고, Anchor Box도 도입했지만, YOLO가 Pooling layer를 사용해서, feature map의 정보들이 layer를 지나면 지날 수록 계속 작아지게 됩니다. 저자는 YOLO를 다양한 이미지들 속에서 강인하게 만들고 싶어서 모델 학습시 Input Size를 변경해주면서 학습해주자고 합니다. 몇몇 iteration마다 model의 input 크기를 변경해주게 되는데, 10 batch 마다 model의 downsample factor가 32인걸 고려해서 {320, 352, ..., 608} 중 임의로 image dimension size를 선택하여 학습해주게 됩니다. 따라서 YOLOv2는 최소 (320 x 320}에서 최대 {608x608}의 네트워크에서 학습되게 됩니다. 덕분에 네트워크는 다양한 스케일에 대해서 강인성을 갖게되고, 속도와 accuracy사이에서 쉽게 trade off를 전환할 수 있습니다. 제일 작은 resolution으로 forward operation을 하게되면(해상도 288 x 288) 90 FPS/Fast R-CNN정도의 mAP로 detection을 할 수 있고, 제일 큰 resolution(608x608)일 경우에는 VOC2007에서 78.6mAP를 갖으면서 여전히 real-time speed를 갖는 네트워크 모델로 사용할 수 있습니다.
2-8. Further Experiments
추가적으로 YOLO v2와 다른 Object Detection System간의 벤치마킹 결과입니다.
3. Faster
일반적으로 다른 Detection System들은 VGG16이나 기존에 나와있는 Feature Extractor를 사용하게 되는데, 저자는 YOLO가 정확도는 높으면서 속도는 빠른 네트워크를 만들고 싶어서 새로운 Feature Extractor Network를 만들어 제안합니다.
3-1. Darknet-19
저자는 Darknet-19라는 새로운 Classification Model을 제안합니다. 잘 알려진데로 큰 사이즈의 kernel filter가 3x3 filter와 여러 layer를 이용하면 큰 크기의 kernel filter가 대체될수 있다고 해서 3x3 filter kenel을 사용하고, Network in Network 논문을 따라서 global average pooling을 사용해서 예측할 뿐만 아니라 1x1 filter를 사용해서 3x3 convolution feature map을 압축하는 방식을 사용하고, batch normalization을 사용해서 regularization을 했다고 합니다. 이렇게 Darknet 19라는 모델을 만들었고 이는 19개의 Convolutional layer와 5개의 pooling layer로 이루어져있는 네트워크입니다. 학습시 weight decay fator는 0.0005를 사용했고 momentum은 0.9, SSD와 유사한 방식의 data augmentation인 random crop, color shifting 등을 사용했다고 합니다.
3-2. Training for classification
3-3. Training for detection
Darknet-19를 ImageNet에 학습시키고, Detection model로 어떻게 변환했는지에 대한 이야기입니다. 해당 부분도 생략하겠습니다.
4. Stronger
4-1. Hierarchical classification
따라서 최종 multi-label 결과에서 최종 class score를 구하려면 다음과 같이 구하면 됩니다.
학습시, 만약 label이 Norfolk terrier라고 한다면, 위에서 만든 tree를 역추적해서 이게 포유류인지, 등등의 대분류 카테고리를 알 수 있기 때문에 이를 이용해 multi-label을 학습시킬 수 있습니다.