본문 바로가기

수업 정리(개인용)/cs231n

CS231n Lecture 11 : Detection and Segmentation

Classification 외에 이런 task에 대해 배워 볼 것이다.

Semantic Segmentation은 pixel-wise classification이다.

Classification + Localization은 하나의 object에 대해 수행하는 detection이다.

Object detection은 거기서 object가 여러 개 나올 수 있다는 점만 다르다.

Instance Segmentation은 Semantic Segmentation에서, 같은 class도 instance 별로 구분할 수 있다.

 

우측 하단의 그림을 보면 semantic segmentation에서는 각 pixel이 cow인지만 관심이 있고, cow class의 instance 별로 구분을 짓지는 않고 있다.

 

이 문제를 어떻게 풀까?

 

1. Sliding window로 window의 center pixel을 classification하고, 이걸 전체 pixel에 대해 다 한다. -X

-Sliding window를 하면서 각 patch별로 계산의 중복이 일어남. 비효율적임.

 

2. 통째로 CNN에 넣어서 H랑 W를 유지하며 결과를 뽑는다. 메모리를 엄청나게 잡아먹을 것이다. 

 

그래서 실제로는 이런 encoder-decoder 구조처럼 생긴, bottle neck이 있는 구조를 많이 사용한다. Decoder 단에서 upsampling을 어떻게 할까?

 

자기 자신으로 다 덮거나, 0으로 덮어서 upsampling 하는 방법도 있지만, 이건 learnable 하지 않다.

 

Max unpooling이라는 것도 있다. Encoder가 손실시킨 정보를 복원해야 하므로, 짝이 맞게 설계해야 할 것이다. 위와 같이 max pooling에서 어느 위치의 값을 살렸는지 position을 기억해뒀다가, upsampling시에 그 부분이 다시 최대가 되도록 되돌린다는 아이디어이다. 위에 소개한 방법보다는 나아보이지만 역시 learnable하지 않다.

 

Transpose Convolution에서는 conv와 반대로, 하나의 scalar 값이 filter와 곱해져서 matrix를 만들게 된다. Conv에서는 matrix가 filter와 곱해져서 scalar가 되었던 것을 기억하자. Overlap 부분은 sum 하는데, 여기서 magnitude의 차이가 생기게 되어 checkerboard artifact가 발생한다는 점이 지적되었다. Overlap이 안일어나게 설계하거나 다른 방법을 쓰자. 다른 이름으로는 deconvolution, upconvolution, fractionally strided convolution, backward strided convolution이 있다.

 

Output에 bounding box regression을 추가하고 multi-task loss로 해결한다. 여러 loss가 있을 경우 가중치를 조절해서 하나의 total loss로 합치는데, 이 가중치는 hyperparameter이면서도 loss의 값을 바꾸기 때문에 loss만으로 tuning이 힘들고 다른 metric을 써야 한다. 주로 transfer learning을 사용한다.

 

Localization이랑은 좀 다른 문제이지만, 저런 regression 방법을 여러 군데 적용해서 pose estimation을 할 수 있다.

 

Object detection으로 넘어와서, 여기서는 object 개수를 모르기 때문에 위처럼 풀 수가 없다. FCN의 ouptut size는 고정되어 있다는 점을 기억하자. 여기서도 naive하게 sliding window + classification으로 생각할 수 있는데, 이미지의 모든 공간에 대해, 모든 b box 의 H와 W에 대해 수행하는 것은 사실상 불가능하다.

 

그래서 selective search같은 알고리즘으로 먼저 region proposal을 찾고, 거기에 대해 classification을 하자는 R-CNN이 등장한다. R-CNN 리뷰 : yun905.tistory.com/13?category=876803

 

 

R-CNN에는 여러 문제가 있었는데, conv 계산을 공유하지 못하다 보니 느리고, 디스크 공간이 많이 필요하고, 고정된 input이 필요하므로 warping 하느라 정보가 손실되고 구조가 불필요하게 복잡하고 등등... SPPNet과 Fast R-CNN에서 그 문제들을 해결했다.

SPPNet 리뷰 : yun905.tistory.com/19?category=876803

Fast R-CN 리뷰 : yun905.tistory.com/20?category=876803

 

Fast R-CNN은 엄청 빠르지만, 아직도 selective search로 region proposal을 한다. 여기서 전체 inference time의 86%가 소요된다. 이걸 end to end 딥러닝으로 바꾸면, cpu bottleneck을 없애서 더 빠르게 할 수 있을 것 같다. 

 

그게 Faster R-CNN이다. Region proposal network가 selective search 대신에 삽입되었다. 여기서 궁금할 수 있는게, 저 새로 생긴 RPN에 대한 label은 대체 어떻게 만드느냐는 것이다. 매 번 다른 b box를 예측할텐데, 그게 object인지 아닌지 어떻게 label을 달까? 설명을 들어 보면 ground truth b box와 IoU같은걸 재서 훈련을 시키는 것 같다. 그렇다면 이제 왜 두 개의 bounding box regression이 필요한 지도 이해가 간다. RPN에서는 제시한 b box가 ground truth와 어느정도 오버랩만 일어나면 되기 때문에 그렇게만 학습을 할 것이고, 이제 그 b box를 정확한 위치로 다듬는 것을 한 번 더 해야 할 것이다.

 

이런 single shot method에는 RPN이 따로 없다. 미리 이미지를 grid로 나누고, 각 grid 별로 B개의 b box를 뽑아서 offset, confidence와 class를 예측하게 하고, 이와 대응되는 label과 한 번에 loss 계산이 이루어진다. 더 빠르지만 덜 정확하다고 한다. 각 grid별로 뽑은 B개의 b box의 class가 서로 다르면 어떻게 될까? Background일 경우 b box regression을 안해야 하는데 이건 어떻게 했을까? 이미지를 region proposal 별로 patch로 넣어주는게 아니고, bounding box 정보들이랑 전체 이미지를 넣으면, 네트워크가 알아서 그 벡터를 bounding box라고 인식하고 각 부분에 대한 classification을 한다는 것인데, 딱 들었을 때는 안될 것 같은데 요즘 많이 쓴다. 자세한 건 논문을 봐야 알 것 같다. Region proposal 류보다 빠르고 성능은 떨어진다.

 

이건 저스틴 존슨이랑 안드레 카파시가 한 연구인데, classification이 아니라 captioning을 적용했다.

 

Instance segmentation이 어려운 문제인데, 각 object의 image patch를 가지고 semantic segmentation을 하는 문제로 환원할 수 있지 않을까? Faster R-CNN을 이용해서 이미지를 object별 patch로 자르고(bounding box를 치고), 그걸 넣어주면 마지막 단의 CNN 입장에서는 그런 patch + class 정보까지 있으므로 여기서 semantic segmentation을 하기는 쉬울 것이다. 

결과는 정말 좋다.

Pose estimation에서도 mask R-CNN이 잘 한다고 하는데, 살짝 의아했던게 여기서 pose estimation에 해당하는 joint coordinates regression은 Faster R-CNN 출력단에 끼워 넣은 것인데 Faster R-CNN이 pose estimation을 잘 한다고 해야 맞지 않을까? Mask R-CNN은 위에서 하던대로 instance segmentation으로 사람 위치를 pixel wise로 특정하는 일을 하고 있다. 

 

어쨌든 결과는 너무 신기하다.

 

Object detection에서 주로 사용되는 COCO는 200K정도의 데이터를 가지고 있다는데, 앞으로는 적은 데이터로 잘 하는 모델을 만드는 게 화두가 될 거라고 하고 마무리를 짓는다.