Feature Extraction(특징을 추출하는 부분)에는 Convolution, ReLU, Max Pooling 이 3가지의 레이어로 층층이 쌓여있다.
Fully Connected Layer에서는 결과를 예측해 낸다고 보면된다.
예를 들어 앵무새를 비유하면 얼굴의 모양, 색상 등등의 특징들, 패턴들을 Convolution이 가져온다.
그리고 점점더 갈 수록 디테일 하게 특징중에서 특징을 뽑아서 거쳐가는게 CNN이라고 볼 수 있다.
이후, CNN에서 패턴(특징)들을 가져와서 Fully Connected Layer에서 결과를 예측해 볼수 있다.
특징을 뽑는 과정은 방법은 많지만, 위의 3가지방법을 주로 사용한다.
Filter bank에서 특징들을 Input image에 합성하면 Feature maps의 결과가 나오게 된다. 이러한 특징들을 강조시켜서
하얗거나 검은부분을 잡아 낼 수 있다. 그래서 결론을 내리면, 이렇게 합성되어 강조된 각 Feature maps들이 모여서
결정을 내릴때 중요한 판단을 할때 도움이 된다. 위와같은 경우에는 명암으로인해 나온 Feature maps이다.
Pooling Layer중에서 Max Pooling은
이전 단계에서 뽑은 특징들(Feature maps)에서 일정한 범위를 정하고 수치가 높은 것들만 뽑아서 추출해내서 압축해 낸다고 보면된다. 위 그림을 보면 알 수있다.
(Output feature map의 사진을 보면, input feature에서 범위마다 큰 값을 가져와 저장한 것을 볼 수 있다.)
Activation Function또는 ReLU라고 부르는데 이 함수는 이전 단계에서 뽑은 특징(Output feature map)에서 불 필요한 요소들을 제거 시켜준다. 예를들어, 위의 표의 그래프를 보면 이하인 값들을 없애 준다.
위와같이 3가지 (Convolution, ReLU, Max Pooling)의 레이어 들을 거치면서 중요하고 특징적인 것 들만 잡아 간다고 생각하면 된다.
결국 마지막에, Fully Connected로 연산해서 예측을 한다고 보면 된다.
선 하나가 y=wx+b 의 수식을 갖고 있는데, x로 값이 들어가면 y로 값이 나오는데, x로 들어간 인자는
weight, bias로 연산 처리된다.
음,,, 한 마디로 y(결과값)이 9가 나오기 위해 weigth 와 bias가 유도를 해준다고 보면된다.
LeNet은 CNN을 처음으로 개발한 얀 르쿤(Yann Lecun) 연구팀이 1998년에 개발한 CNN 알고리즘의 이름이다. original 논문 제목은 "Gradient-based learning applied to document recognition"이다. 우선 LeNet-5의 구조를 살펴보자.
그림에서 볼 수 있듯이 LeNet-5는 인풋, 3개의 컨볼루션 레이어(C1, C3, C5), 2개의 서브샘플링 레이어(S2, S4), 1층의 full-connected 레이어(F6), 아웃풋 레이어로 구성되어 있다. 참고로 C1부터 F6까지 활성화 함수로 tanh을 사용한다.
우선 Convolution과 ReLu(Activation Function)을 사용하고 Subsampling에서 이미지의 크기를 작게 압축(pooling)시킨다. 그런다음에 또 Convolution, ReLU, pooling작업을 통해 다시 Subsampling을 하고, 마지막에 Fully Connected를 통해 Output을 Classification해낸다고 보면된다.
1) C1 레이어: 입력 영상(여기서는 32 x 32 사이즈의 이미지)을 6개의 5 x 5 필터와 컨볼루션 연산을 해준다. 그 결과 6장의 28 x 28 특성 맵을 얻게 된다.
훈련해야할 파라미터 개수: (가중치*입력맵개수 + 바이어스)*특성맵개수 = (5*5*1 + 1)*6 = 156
2) S2 레이어: 6장의 28 x 28 특성 맵에 대해 서브샘플링을 진행한다. 결과적으로 28 x 28 사이즈의 특성 맵이 14 x 14 사이즈의 특성맵으로 축소된다. 2 x 2 필터를 stride 2로 설정해서 서브샘플링해주기 때문이다. 사용하는 서브샘플링 방법은 평균 풀링(average pooling)이다.
훈련해야할 파라미터 개수: (가중치 + 바이어스)*특성맵개수 = (1 + 1)*6 = 12
평균풀링인데 왜 훈련해야할 파라미터가 필요한지 의아할 수 있는데, original 논문에 의하면 평균을 낸 후에 한 개의 훈련가능한 가중치(trainable weight)를 곱해주고 또 한 개의 훈련가능한 바이어스(trainable bias)를 더해준다고 한다. 그 값이 시그모이드 함수를 통해 활성화된다. 참고로 그 가중치와 바이어스는 시그모이드의 비활성도를 조절해준다고 한다.
3) C3 레이어: 6장의 14 x 14 특성맵에 컨볼루션 연산을 수행해서 16장의 10 x 10 특성맵을 산출해낸다. 이것 이해하는데 한참 걸렸다. 참고자료[4]가 이해하는데 큰 도움이 되었다. 아마도 지금 이해한 것이 맞을 것이다. (혹시나 틀렸다면 누군가 알려주시길.)
6장의 14 x 14 특성맵에서 연속된 3장씩을 모아서 5 x 5 x 3 사이즈의 필터와 컨볼루션 해준다(그림2에서 열0-5). 6장의 10 x 10 특성맵이 산출된다.
또한 6장의 14 x 14 특성맵에서 연속된 4장씩을 모아서 5 x 5 x 4 사이즈의 필터와 컨볼루션 해준다(그림2에서 열6-11). 6장의 10 x 10 특성맵이 산출된다.
또한 6장의 14 x 14 특성맵에서 불연속한 4장씩을 모아서 5 x 5 x 4 사이즈의 필터와 컨볼루션 해준다(그림2에서 열12-14). 3장의 10 x 10 특성맵이 산출된다.
마지막으로 6장의 14 x 14 특성맵 모두를 가지고 5 x 5 x 6 사이즈의 필터와 컨볼루션 해준다(그림2에서 열15). 1장의 10 x 10 특성맵이 산출된다.
결과적으로 16장(6 + 6 + 3 + 1)의 10 x 10 특성맵을 얻게 되었다.
그림2. C3에서 6장의 14 x 14 특성맵을 조합하는 방법
훈련해야할 파라미터 개수:
첫번째그룹=> (가중치*입력맵개수+바이어스)*특성맵 개수 = (5*5*3 + 1)*6 = 456
두번째그룹=> (가중치*입력맵개수+바이어스)*특성맵 개수 = (5*5*4 + 1)*6 = 606
세번째그룹=> (가중치*입력맵개수+바이어스)*특성맵 개수 = (5*5*4 + 1)*3 = 303
네번째그룹=> (가중치*입력맵개수+바이어스)*특성맵 개수 = (5*5*6 + 1)*1 = 151
456 + 606 + 303 + 151 = 1516
4) S4 레이어: 16장의 10 x 10 특성 맵에 대해서 서브샘플링을 진행해 16장의 5 x 5 특성 맵으로 축소시킨다.
훈련해야할 파라미터 개수: (가중치 + 바이어스)*특성맵개수 = (1 + 1)*16 = 32
5) C5 레이어: 16장의 5 x 5 특성맵을 120개 5 x 5 x 16 사이즈의 필터와 컨볼루션 해준다. 결과적으로 120개 1 x 1 특성맵이 산출된다.
훈련해야할 파라미터 개수: (가중치*입력맵개수 + 바이어스)*특성맵 개수 = (5*5*16 + 1)*120 = 48120
6) F6 레이어: 84개의 유닛을 가진 피드포워드 신경망이다. C5의 결과를 84개의 유닛에 연결시킨다.
훈련해야할 파라미터 개수: 연결개수 = (입력개수 + 바이어스)*출력개수 = (120 + 1)*84 = 10164
7) 아웃풋 레이어: 10개의 Euclidean radial basis function(RBF) 유닛들로 구성되어있다. 각각 F6의 84개 유닛으로부터 인풋을 받는다. 최종적으로 이미지가 속한 클래스를 알려준다.
LeNet-5를 제대로 가동하기 위해 훈련해야할 파라미터는 총 156 + 12 + 1516 + 32 + 48120 + 10164 = 60000개다.
Convolution과 ReLU를 사용한뒤 pooling을 하고, 또 반복해서 마지막에 Fully connected를 해줘서 예측한다.
AlexNet의 기본구조는 LeNet-5와 크게 다르지 않다. 2개의 GPU로 병렬연산을 수행하기 위해서 병렬적인 구조로 설계되었다는 점이 가장 큰 변화이다. AlexNet의 구조도를 살펴보자
AlexNet은 8개의 레이어로 구성되어 있다. 5개의 컨볼루션 레이어와 3개의 full-connected 레이어로 구성되어 있다. 두번째, 네번째, 다섯번째 컨볼루션 레이어들은 전 단계의 같은 채널의 특성맵들과만 연결되어 있는 반면, 세번째 컨볼루션 레이어는 전 단계의 두 채널의 특성맵들과 모두 연결되어 있다는 것을 집고 넘어가자.
이제 각 레이어마다 어떤 작업이 수행되는지 살펴보자. 우선 AlexNet에 입력 되는 것은 227 x 227 x 3 이미지다. (227 x 227 사이즈의 RGB 컬러 이미지를 뜻한다.) 그림에는 224로 되어 있는데 잘못된 겁니다(227로 생각하기.).
1) 첫번째 레이어(컨볼루션 레이어): 96개의 11 x 11 x 3 사이즈 필터커널로 입력 영상을 컨볼루션해준다. 컨볼루션 보폭(stride)를 4로 설정했고, zero-padding은 사용하지 않았다. zero-padding은 컨볼루션으로 인해 특성맵의 사이즈가 축소되는 것을 방지하기 위해, 또는 축소되는 정도를 줄이기 위해 영상의 가장자리 부분에 0을 추가하는 것이다. 결과적으로 55 x 55 x 96 특성맵(96장의 55 x 55 사이즈 특성맵들)이 산출된다. 그 다음에 ReLU 함수로 활성화해준다. 이어서 3 x 3 overlapping max pooling이 stride 2로 시행된다. 그 결과 27 x 27 x 96 특성맵을 갖게 된다. 그 다음에는 수렴 속도를 높이기 위해 local response normalization이 시행된다. local response normalization은 특성맵의 차원을 변화시키지 않으므로, 특성맵의 크기는 27 x 27 x 96으로 유지된다.
* 컨볼루션 이후 특성맵의 사이즈가 어떻게 결정되는지에 대해서 의문을 가질 분들이 계실 것 같습니다. 그래서 이에 대한 내용을 AlexNet보다 이후에 나온 모델들인 VGG-F, VGG-M, VGG-S을 설명하면서 하단부에 소개했으니 참고하시기 바랍니다.=> https://bskyvision.com/420
2) 두번째 레이어(컨볼루션 레이어): 256개의 5 x 5 x 48 커널을 사용하여 전 단계의 특성맵을 컨볼루션해준다. stride는 1로, zero-padding은 2로 설정했다. 따라서 27 x 27 x 256 특성맵(256장의 27 x 27 사이즈 특성맵들)을 얻게 된다. 역시 ReLU 함수로 활성화한다. 그 다음에 3 x 3 overlapping max pooling을 stride 2로 시행한다. 그 결과 13 x 13 x 256 특성맵을 얻게 된다. 그 후 local response normalization이 시행되고, 특성맵의 크기는 13 x 13 x 256으로 그대로 유지된다.
3) 세번째 레이어(컨볼루션 레이어): 384개의 3 x 3 x 256 커널을 사용하여 전 단계의 특성맵을 컨볼루션해준다. stride와 zero-padding 모두 1로 설정한다. 따라서 13 x 13 x 384 특성맵(384장의 13 x 13 사이즈 특성맵들)을 얻게 된다. 역시 ReLU 함수로 활성화한다.
4) 네번째 레이어(컨볼루션 레이어): 384개의 3 x 3 x 192 커널을 사용해서 전 단계의 특성맵을 컨볼루션해준다. stride와 zero-padding 모두 1로 설정한다. 따라서 13 x 13 x 384 특성맵(384장의 13 x 13 사이즈 특성맵들)을 얻게 된다. 역시 ReLU 함수로 활성화한다.
5) 다섯번째 레이어(컨볼루션 레이어): 256개의 3 x 3 x 192 커널을 사용해서 전 단계의 특성맵을 컨볼루션해준다. stride와 zero-padding 모두 1로 설정한다. 따라서 13 x 13 x 256 특성맵(256장의 13 x 13 사이즈 특성맵들)을 얻게 된다. 역시 ReLU 함수로 활성화한다. 그 다음에 3 x 3 overlapping max pooling을 stride 2로 시행한다. 그 결과 6 x 6 x 256 특성맵을 얻게 된다.
6) 여섯번째 레이어(Fully connected layer): 6 x 6 x 256 특성맵을 flatten해줘서 6 x 6 x 256 = 9216차원의 벡터로 만들어준다. 그것을 여섯번째 레이어의 4096개의 뉴런과 fully connected 해준다. 그 결과를 ReLU 함수로 활성화한다.
7) 일곱번째 레이어(Fully connected layer): 4096개의 뉴런으로 구성되어 있다. 전 단계의 4096개 뉴런과 fully connected되어 있다. 출력 값은 ReLU 함수로 활성화된다.
8) 여덟번째 레이어(Fully connected layer): 1000개의 뉴런으로 구성되어 있다. 전 단계의 4096개 뉴런과 fully connected되어 있다. 1000개 뉴런의 출력값에 softmax 함수를 적용해 1000개 클래스 각각에 속할 확률을 나타낸다.
총, 약 6천만개의 파라미터가 훈련되어야 한다. LeNet-5에서 6만개의 파라미터가 훈련되야했던 것과 비교하면 천배나 많아졌다. 하지만 그만큼 컴퓨팅 기술도 좋아졌고, 훈련시간을 줄이기 위한 방법들도 사용되었기 때문에 훈련이 가능했다. 예전 기술 같으면 상상도 못할 연산량이다.
AlexNet 좀 더 깊이 들여다보기
1) ReLU 함수: 활성화 함수로는 LeNet-5에서 사용되었던 Tanh 함수 대신에 ReLU 함수가 사용되었다. ReLU는 rectified linear unit의 약자이다. 같은 정확도를 유지하면서 Tanh을 사용하는 것보다 6배나 빠르다고 한다. AlexNet 이후에는 활성화함수로 ReLU 함수를 사용하는 것이 선호되고 있다.
그림2. tanh 함수와 ReLU 함수 [2]
2) dropout: 과적합(over-fitting)을 막기 위해서 규제 기술의 일종인 dropout을 사용했다. dropout이란 fully-connected layer의 뉴런 중 일부를 생략하면서 학습을 진행하는 것이다[5]. 몇몇 뉴런의 값을 0으로 바꿔버린다. 따라서 그 뉴런들은 forward pass와 back propagation에 아무런 영향을 미치지 않는다. dropout은 훈련시에 적용되는 것이고, 테스트시에는 모든 뉴런을 사용한다.
그림3. dropout 설명 [2]
3) overlapping pooling: CNN에서 pooling의 역할은 컨볼루션을 통해 얻은 특성맵의 크기를 줄이기 위함이다. LeNet-5의 경우 평균 풀링(average pooling)이 사용된 반면, AlexNet에서는 최대 풀링(max pooling)이 사용되었다. 또한 LeNet-5의 경우 풀링 커널이 움직이는 보폭인 stride를 커널 사이즈보다 작게 하는 overlapping pooling을 적용했다. 따라서 정확히 말하면 LeNet-5는 non-overlapping 평균 풀링을 사용한 것이고, AlexNet은 overlapping 최대 풀링을 사용한 것이다.
overlapping 풀링과 non-overlapping 풀링을 비교한 그림은 아래와 같다. 편의를 위해 최대 풀링인 경우로 설명했다.
그림4. non-overlapping pooling과 overlapping pooling 비교
overlapping 풀링을 하면 풀링 커널이 중첩되면서 지나가는 반면, non-overlapping 풀링을 하면 중첩없이 진행된다. overlapping 풀링이 top-1, top-5 에러율을 줄이는데 좀 더 효과가 있다고 한다.
4) local response normalization (LRN): 신경생물학에는 lateral inhibition이라고 불리는 개념이 있다. 활성화된 뉴런이 주변 이웃 뉴런들을 억누르는 현상을 의미한다. lateral inhibition 현상을 모델링한 것이 바로 local response normalization이다. 강하게 활성화된 뉴런의 주변 이웃들에 대해서 normalization을 실행한다. 주변에 비해 어떤 뉴런이 비교적 강하게 활성화되어 있다면, 그 뉴런의 반응은 더욱더 돋보이게 될 것이다. 반면 강하게 활성화된 뉴런 주변도 모두 강하게 활성화되어 있다면, local response normalization 이후에는 모두 값이 작아질 것이다.
5) data augmentation: 과적합을 막기 위해 dropout 말고도 또다른 방법이 사용되었다. 과적합을 막는 가장 좋은 방법 중 하나는 데이터의 양을 늘리는 것이다. 훈련시킬 때 적은 양의 데이터를 가지고 훈련시킬 경우 과적합될 가능성이 크기 때문이다. 따라서 AlexNet의 개발자들은 data augmentation이란 방법을 통해 데이터의 양을 늘렸다.
그림5. data augmentation
쉽게 말해서 하나의 이미지를 가지고 여러 장의 비슷한 이미지를 만들어 내는 것이다. 이미지를 좌우 반전시키거나, AlexNet이 허용하는 입력 이미지 크기인 227 x 227 x 3보다 좀 더 큰 이미지를 조금씩 다르게 잘라서 227 x 227 x 3으로 만들어줘서 여러 장을 만들어낸다. 같은 내용을 담고 있지만 위치가 살짝 다른 이미지들이 생산된다.
옥스포드 대학의 연구팀 VGG에 의해 개발된 모델로써, 2014년 이미지넷 이미지 인식 대회에서 준우승을 한 모델이다. 여기서 말하는 VGGNet은 16개 또는 19개의 층으로 구성된 모델을 의미한다(VGG16, VGG19로 불림). 이전에 포스팅한 VGG-F, VGG-M, VGG-S와는 차이가 있다. 그 모델들은 8개의 층을 가진 AlexNet과 유사한 모델들이다. 하지만 AlexNet와 같이 병렬적 구조로 이뤄지진 않았다.
역사적으로 봤을 때 VGGNet 모델부터 시작해서 네트워크의 깊이가 확 깊어졌다. 아래 그림을 참고하자.
네트워크의 깊이 변화에 따른 top-5 error의 변화 [1]
2012년, 2013년 우승 모델들은 8개의 층으로 구성되었었다. 반면 2014년의 VGGNet(VGG19)는 19층으로 구성되었고, 또한 GoogLeNet은 22층으로 구성되었다. 그리고 2015년에 이르러서는 152개의 층으로 구성된 ResNet이 제안되었다. 네크워크가 깊어질 수록 성능이 좋아졌음을 위 그림을 통해 확인할 수 있다. VGGNet은 사용하기 쉬운 구조와 좋은 성능 덕분에 그 대회에서 우승을 거둔 조금 더 복잡한 형태의 GoogLeNet보다 더 인기를 얻었다.
자, 그러면 VGGNet은 이전 모델들과 비교해서 어떤 점이 있는지 살펴보도록 하자. 이 VGGNet의 original 논문은 Karen Simonyan과 Andrew Zisserman에 의해 2015 ICLR에 게재된 "Very deep convolutional networks for large-scale image recognition"이다.
VGGNet의 구조
VGGNet의 original 논문의 개요에서 밝히고 있듯이 이 연구의 핵심은 네트워크의 깊이를 깊게 만드는 것이 성능에 어떤 영향을 미치는지를 확인하고자 한 것이다. VGG 연구팀은 깊이의 영향만을 최대한 확인하고자 컨볼루션 필터커널의 사이즈는 가장 작은 3 x 3으로 고정했다.
개인적으로 나는 모든 필터 커널의 사이즈를 3 x 3으로 설정했기 때문에 네트워크의 깊이를 깊게 만들 수 있다고 생각한다. 왜냐하면 필터커널의 사이즈가 크면 그만큼 이미지의 사이즈가 금방 축소되기 때문에 네트워크의 깊이를 충분히 깊게 만들기 불가능하기 때문이다.
VGG 연구팀은 original 논문에서 총 6개의 구조(A, A-LRN, B, C, D, E)를 만들어 성능을 비교했다. 여러 구조를 만든 이유는 기본적으로 깊이의 따른 성능 변화를 비교하기 위함이다. 이중 D 구조가 VGG16이고 E 구조가 VGG19라고 보면 된다.
VGGNet 구조 설명 표 [출처: original 논문]
VGG 연구팀은 AlexNet과 VGG-F, VGG-M, VGG-S에서 사용되던 Local Response Normalization(LRN)이 A 구조와 A-LRN 구조의 성능을 비교함으로 성능 향상에 별로 효과가 없다고 실험을 통해 확인했다. 그래서 더 깊은 B, C, D, E 구조에는 LRN을 적용하지 않는다고 논문에서 밝혔다. 또한 그들은 깊이가 11층, 13층, 16층, 19층으로 깊어지면서 분류 에러가 감소하는 것을 관찰했다. 즉, 깊어질수록 성능이 좋아진다는 것이었다.
VGGNet의 구조를 깊이 들여다보기에 앞서 먼저 집고 넘어가야할 것이 있다. 그것은 바로 3 x 3 필터로 두 차례 컨볼루션을 하는 것과 5 x 5 필터로 한 번 컨볼루션을 하는 것이 결과적으로 동일한 사이즈의 특성맵을 산출한다는 것이다(아래 그림 참고). 3 x 3 필터로 세 차례 컨볼루션 하는 것은 7 x 7 필터로 한 번 컨볼루션 하는 것과 대응된다.
그러면 3 x 3 필터로 세 차례 컨볼루션을 하는 것이 7 x 7 필터로 한 번 컨볼루션하는 것보다 나은 점은 무엇일까? 일단 가중치 또는 파라미터의 갯수의 차이다. 3 x 3 필터가 3개면 총 27개의 가중치를 갖는다. 반면 7 x 7 필터는 49개의 가중치를 갖는다. CNN에서 가중치는 모두 훈련이 필요한 것들이므로, 가중치가 적다는 것은 그만큼 훈련시켜야할 것의 갯수가 작아진다. 따라서 학습의 속도가 빨라진다. 동시에 층의 갯수가 늘어나면서 특성에 비선형성을 더 증가시키기 때문에 특성이 점점 더 유용해진다.
VGG16 구조 분석
그러면 이제 VGG16(D 구조)를 예시로, 각 층마다 어떻게 특성맵이 생성되고 변화되는지 자세하게 살펴보자. 아래 구조도와 함께 각 층의 세부사항을 읽어나가면 이해하기가 그렇게 어렵지 않을 것이다.
VGG16 구조 [6]
0) 인풋: 224 x 224 x 3 이미지(224 x 224 RGB 이미지)를 입력받을 수 있다.
1) 1층(conv1_1): 64개의 3 x 3 x 3 필터커널로 입력이미지를 컨볼루션해준다. zero padding은 1만큼 해줬고, 컨볼루션 보폭(stride)는 1로 설정해준다. zero padding과 컨볼루션 stride에 대한 설정은 모든 컨볼루션층에서 모두 동일하니 다음 층부터는 설명을 생략하겠다. 결과적으로 64장의 224 x 224 특성맵(224 x 224 x 64)들이 생성된다. 활성화시키기 위해 ReLU 함수가 적용된다. ReLU함수는 마지막 16층을 제외하고는 항상 적용되니 이 또한 다음 층부터는 설명을 생략하겠다.
2) 2층(conv1_2): 64개의 3 x 3 x 64 필터커널로 특성맵을 컨볼루션해준다. 결과적으로 64장의 224 x 224 특성맵들(224 x 224 x 64)이 생성된다. 그 다음에 2 x 2 최대 풀링을 stride 2로 적용함으로 특성맵의 사이즈를 112 x 112 x 64로 줄인다.
*conv1_1, conv1_2와 conv2_1, conv2_2등으로 표현한 이유는 해상도를 줄여주는 최대 풀링 전까지의 층등을 한 모듈로 볼 수 있기 때문이다.
3) 3층(conv2_1): 128개의 3 x 3 x 64 필터커널로 특성맵을 컨볼루션해준다. 결과적으로 128장의 112 x 112 특성맵들(112 x 112 x 128)이 산출된다.
4) 4층(conv2_2): 128개의 3 x 3 x 128 필터커널로 특성맵을 컨볼루션해준다. 결과적으로 128장의 112 x 112 특성맵들(112 x 112 x 128)이 산출된다. 그 다음에 2 x 2 최대 풀링을 stride 2로 적용해준다. 특성맵의 사이즈가 56 x 56 x 128로 줄어들었다.
5) 5층(conv3_1): 256개의 3 x 3 x 128 필터커널로 특성맵을 컨볼루션한다. 결과적으로 256장의 56 x 56 특성맵들(56 x 56 x 256)이 생성된다.
6) 6층(conv3_2): 256개의 3 x 3 x 256 필터커널로 특성맵을 컨볼루션한다. 결과적으로 256장의 56 x 56 특성맵들(56 x 56 x 256)이 생성된다.
7) 7층(conv3_3): 256개의 3 x 3 x 256 필터커널로 특성맵을 컨볼루션한다. 결과적으로 256장의 56 x 56 특성맵들(56 x 56 x 256)이 생성된다. 그 다음에 2 x 2 최대 풀링을 stride 2로 적용한다. 특성맵의 사이즈가 28 x 28 x 256으로 줄어들었다.
8) 8층(conv4_1): 512개의 3 x 3 x 256 필터커널로 특성맵을 컨볼루션한다. 결과적으로 512장의 28 x 28 특성맵들(28 x 28 x 512)이 생성된다.
9) 9층(conv4_2): 512개의 3 x 3 x 512 필터커널로 특성맵을 컨볼루션한다. 결과적으로 512장의 28 x 28 특성맵들(28 x 28 x 512)이 생성된다.
10) 10층(conv4_3): 512개의 3 x 3 x 512 필터커널로 특성맵을 컨볼루션한다. 결과적으로 512장의 28 x 28 특성맵들(28 x 28 x 512)이 생성된다. 그 다음에 2 x 2 최대 풀링을 stride 2로 적용한다. 특성맵의 사이즈가 14 x 14 x 512로 줄어든다.
11) 11층(conv5_1): 512개의 3 x 3 x 512 필터커널로 특성맵을 컨볼루션한다. 결과적으로 512장의 14 x 14 특성맵들(14 x 14 x 512)이 생성된다.
12) 12층(conv5_2): 512개의 3 x 3 x 512 필터커널로 특성맵을 컨볼루션한다. 결과적으로 512장의 14 x 14 특성맵들(14 x 14 x 512)이 생성된다.
13) 13층(conv5-3): 512개의 3 x 3 x 512 필터커널로 특성맵을 컨볼루션한다. 결과적으로 512장의 14 x 14 특성맵들(14 x 14 x 512)이 생성된다. 그 다음에 2 x 2 최대 풀링을 stride 2로 적용한다. 특성맵의 사이즈가 7 x 7 x 512로 줄어든다.
14) 14층(fc1): 7 x 7 x 512의 특성맵을 flatten 해준다. flatten이라는 것은 전 층의 출력을 받아서 단순히 1차원의 벡터로 펼쳐주는 것을 의미한다. 결과적으로 7 x 7 x 512 = 25088개의 뉴런이 되고, fc1층의 4096개의 뉴런과 fully connected 된다. 훈련시 dropout이 적용된다.
(이 부분을 제대로 이해할 수 있도록 지적해주신 jaist님과 hiska님께 감사드립니다.^^)
15) 15층(fc2): 4096개의 뉴런으로 구성해준다. fc1층의 4096개의 뉴런과 fully connected 된다. 훈련시 dropout이 적용된다.
16) 16층(fc3): 1000개의 뉴런으로 구성된다. fc2층의 4096개의 뉴런과 fully connected된다. 출력값들은 softmax 함수로 활성화된다. 1000개의 뉴런으로 구성되었다는 것은 1000개의 클래스로 분류하는 목적으로 만들어진 네트워크란 뜻이다.
ResNet은 마이크로소프트에서 개발한 알고리즘이다. 그것도 북경연구소의 중국인 연구진이 개발한 알고리즘이다. ResNet의 original 논문명은 "Deep Residual Learning for Image Recognition"이고, 저자는 Kaiming He, Xiangyu Zhang, Shaoqing Ren, Jiao Sun으로 전부 다 중국인이다.
층수에 있어서 ResNet은 급속도로 깊어진다. 2014년의 GoogLeNet이 22개 층으로 구성된 것에 비해, ResNet은 152개 층을 갖는다. 약 7배나 깊어졌다!
위 그림을 보면 네트워크가 깊어지면서 top-5 error가 낮아진 것을 확인할 수 있다. 한마디로 성능이 좋아진 것이다. 그렇다면 질문! "망을 깊게하면 무조건 성능이 좋아질까?" 이것을 확인하기 위해 ResNet의 저자들은 컨볼루션 층들과 fully-connected 층들로 20 층의 네트워크와 56층의 네트워크를 각각 만든 다음에 성능을 테스트해보았다.
위 그래프들을 보면 오히려 더 깊은 구조를 갖는 56층의 네트워크가 20층의 네트워크보다 더 나쁜 성능을 보임을 알 수 있다. 기존의 방식으로는 망을 무조건 깊게 한다고 능사가 아니라는 것을 확인한 것이다. 뭔가 새로운 방법이 있어야 망을 깊게 만드는 효과를 볼 수 있다는 것을 ResNet의 저자들은 깨달았다.
Residual Block
그것이 바로 ResNet의 핵심인 Residual Block의 출현을 가능케 했다. 아래 그림에서 오른쪽이 Residual Block을 나타낸다. 기존의 망과 차이가 있다면 입력값을 출력값에 더해줄 수 있도록 지름길(shortcut)을 하나 만들어준 것 뿐이다.
기존의 신경망은 입력값 x를 타겟값 y로 매핑하는 함수 H(x)를 얻는 것이 목적이었다. 그러나 ResNet은 F(x) + x를 최소화하는 것을 목적으로 한다. x는 현시점에서 변할 수 없는 값이므로 F(x)를 0에 가깝게 만드는 것이 목적이 된다. F(x)가 0이 되면 출력과 입력이 모두 x로 같아지게 된다. F(x) = H(x) - x이므로 F(x)를 최소로 해준다는 것은 H(x) - x를 최소로 해주는 것과 동일한 의미를 지닌다. 여기서 H(x) - x를 잔차(residual)라고 한다. 즉, 잔차를 최소로 해주는 것이므로 ResNet이란 이름이 붙게 된다.
ResNet의 구조
ResNet은 기본적으로 VGG-19의 구조를 뼈대로 한다. 거기에 컨볼루션 층들을 추가해서 깊게 만든 후에, shortcut들을 추가하는 것이 사실상 전부다. 34층의 ResNet과 거기에서 shortcut들을 제외한 버전인 plain 네트워크의 구조는 다음과 같다.
출처: original 논문
위 그림을 보면 알 수 있듯이 34층의 ResNet은 처음을 제외하고는 균일하게 3 x 3 사이즈의 컨볼루션 필터를 사용했다. 그리고 특성맵의 사이즈가 반으로 줄어들 때, 특성맵의 뎁스를 2배로 높였다.
저자들은 과연 shortcut, 즉 Residual block들이 효과가 있는지를 알기 위해 이미지넷에서 18층 및 34층의 plain 네트워크와 ResNet의 성능을 비교했다.
출처: original 논문
왼쪽 그래프를 보면 plain 네트워크는 망이 깊어지면서 오히려 에러가 커졌음을 알 수 있다. 34층의 plain 네트워크가 18층의 plain 네트워크보다 성능이 나쁘다. 반면, 오른쪽 그래프의 ResNet은 망이 깊어지면서 에러도 역시 작아졌다! shortcut을 연결해서 잔차(residual)를 최소가 되게 학습한 효과가 있다는 것이다.
아래 표는 18층, 34층, 50층, 101층, 152층의 ResNet이 어떻게 구성되어 있는가를 잘 나타내준다. 깊은 구조일수록 성능도 좋다. 즉, 152층의 ResNet이 가장 성능이 뛰어나다.
출처: original 논문
위의 그림은 DenseNet이 가지는 특성을 그림으로 설명해놓았다.
그러니까, 결과적으로 l번째 layer은 이전 모든 0,1,2...l-1 번째의 output들을 입력으로 사용하게 되고, 그 결과인 x_l을 수식으로 표현하자면 다음과 같다.
이 수식에서 중요한 것은 x_0 ... x_l-1 을 더하지(sum) 않고 이어붙였다는(concatenation) 것이다. [x_0 , x_1 , ... x_l-1] 은 모든 input을 이어붙인 것을 나타낸다.
그리고 조금 더 나아가서, 모든 모델을 이렇게 구현하지 않고, 이렇게 이어붙인 Connection의 덩어리를 하나의 Block으로 만들어서 그 덩어리들을 이어붙인것을 총 하나의 모델로 만들었다.
너무 말로 표현하기 추상적이므로 아래의 그림을 참고하자.
Dense Block이라고 부르는 하나의 connection 덩어리를 만들어서 전통적인 CNN처럼 Convolution , Pooling layer과 함께 순차적으로 Dense Block들을 거쳐서 마지막에 Linear layer후 결과를 뽑아내게 된다.
DenseNet의 전반적인 특징을 살펴봤다면 이제 네트워크 구조에 대해 자세히 살펴봅시다. ResNet과 가장 큰 다른 점은 피쳐 맵을 더해주는게 아닌 쌓아가는 과정을 거친다는 것입니다. 배치 노말라이제이션, ReLU 순서 그리고 모델의 하이퍼파라미터인 growth rate k에 대해서도 알아봅시다. 역시나 DenseNet에서도 계산 복잡성을 줄이기 위해 bottleneck 구조를 사용합니다.
* Bottleneck layers
모든 layer가 k output feature를 만들어낸다 하더라도, 일반적으로 훨씬 많은 input을 받아오게 된다.
보통 이런 때 feature map을 줄이기 위해서 3x3 convolution layer앞에 1x1 convolution layer을 추가하는 bottleneck layer을 도입하고는 한다.
그렇기 때문에 DenseNet에서는 bottleneck layer 또한 추가하는 시도를 해 보있다.
합성함수 H = BN -> ReLU -> 1x1Conv -> BN -> ReLU -> 3x3Conv 의 형식이다.
DenseNet architecture 자세히 살펴보기
이 포스트에 사용된 이미지들은 DSBA 연구실 김준홍 박사과정의 세미나 발표자료를 활용하여 편집하였습니다.
이전 포스트에서 언급한 DenseNet의 장점에 대해 다시 요약 해보자면 아래와 같습니다.
- Dense connectivity advantages
- They alleviate the vanishing-gradient problem
- Strengthen feature propagation
- Encourage feature reuse
- Substantially reduce the number of parameters(less complexity)
- Reduce overfitting on tasks with smaller training set sizes.
논문의 저자들이 ResNet 구조랑 굉장히 많은 비교를 하면서 어필하는 장점들입니다. 이는 모두 skip-connection에서 dense connectivity로 바뀌면서 만들어지는 효과라고 볼 수 있습니다.
(사실 이 논문이 나오기 전까지 ResNet이 SOTA(State Of The Art)였기 때문으로 보입니다)
ResNet과 DenseNet 비교 해보기
ResNet은 summation(텐서플로우에서는 tf.add)을 사용하였기 때문에 information flow가 결국 점점 옅어지며 information 흐름을 방해합니다. 하지만 DenseNet은 차곡차곡 쌓아가면서 uncorrelated feature들도 손쉽게 가져가는 구조입니다.
Composite function
배치 노말라이제이션(BN : Batch Normalization), 렐루(ReLU : Rectified Linear Unit), 콘볼루션(Convolution) 순서에 따른 효율성을 연구한 논문을 인용하면서 각 레이어마다 BN, ReLU, Convolution 순서대로 구조를 짭니다.
pooling layers
위 수식의 concatenation(HlHl)은 feature map 사이즈가 변하면 연산이 불가능합니다. 그리고 convolutional network의 가장 큰 특징 중 하나라면 pooling으로 feature map size를 줄이는 것입니다. 그래서 DenseNet은 네트워크 전체를 몇 개의 dense block으로 나눠서 같은 feature map size를 가지는 레이어들은 같은 dense block내로 묶습니다.
위 그림에서는 총 3개의 dense block으로 나뉩니다. 같은 블럭 내의 레이어들은 전부 같은 feature map size를 가지게 되죠. 그리고 빨간 네모를 친 pooling과 convolution 부분을 transition layer라고 부릅니다. 이 레이어에서는 배치 노말라이제이션, feature map dimension을 조절하기 위한 1x1 convolution layer 그리고 2x2 average pooling layer가 위치합니다. 만약 dense block1에서 100x100 size의 feature map을 가지고 있었다면 dense block2에서는 50x50 size의 feature map이 되겠죠?
Growth rate
수식 HlHl이 k개의 feature map을 생성한다고 하면, lthlth 레이어는 k0+k×(l−1)k0+k×(l−1)개의 feature map이 입력된다고 할 수 있습니다. 여기서 k0k0는 dense block 첫 번째의 인풋 레이어의 feature map 갯수입니다. 논문에서는 DenseNet과 기존의 네트워크의 다른 점 중 하나로 매우 좁은 레이어(very narrow layers)를 가지고 있다고 언급합니다. kk를 growth rate 이라고 하며 실험 결과 kk값이 낮아도 state-of-the-art의 결과를 보여준다고 합니다. 아래는 k=6일 경우 feature map이 어떻게 쌓이는지 간단히 도식화 한 그림입니다.
논문에서는 kk값이 작아도 충분한 이유가 레이어를 지나면서 feature map이 효율적으로 정보를 전달하고 있기 때문이라고 하고 있습니다.
Bottleneck layers
이제 각 레이어들이 kk개의 feature map을 생성하면서 쌓아가는 구조라는 것을 이해했으면, 계산 복잡성을 줄이기 위해서 한 가지 작업을 더 거치게 됩니다. 기존 구조는 아래와 같습니다.
BN -> ReLU -> 3x3 Conv의 구조에서 BN -> ReLU -> 1x1 Conv -> BN -> ReLU -> 3x3 Conv의 Bottleneck 구조를 적용합니다. 이는 계산 복잡성을 줄여주는 효과가 있습니다.
Compession
모델을 더 컴팩트하게 만들기 위해서, transition layer에서 feature map의 수를 줄여주는 작업을 하게 됩니다. 아래 그림에서 Dense block 사이에 있는 Convolution layer와 pooling layer를 통틀어 trainsition layer라고 합니다. 만약 dense block을 모두 통과한 feature map의 갯수가 mm개라면 이 trainsition layer를 거치면 θmθm개가 됩니다. 여기서 θθ값은 우리가 지정해주는 하이퍼파라미터(hyper parameter)이며 0보다는 크고 1보다는 작거나 같은 값을 가집니다. 만약 1이라면 feature map의 갯수는 변하지 않고 그대로 계속 쌓여나간다고 할 수 있습니다.
할게 너무 만타... 화이팅......
- 참고 블로그 -
LeNet-5 => https://bskyvision.com/418
AlexNet => https://bskyvision.com/421
VGG-F, VGG-M, VGG-S => https://bskyvision.com/420
VGG-16, VGG-19 => https://bskyvision.com/504
GoogLeNet(inception v1) => https://bskyvision.com/539
ResNet => https://bskyvision.com/644
DenseNet => jayhey.github.io/deep%20learning/2017/10/15/DenseNet_2/
SENet => https://bskyvision.com/640
'workSpace > PYTHON' 카테고리의 다른 글
[ML] 타이타닉 생존자 예측하기 및 설명 (0) | 2021.01.19 |
---|---|
[ML] SVM을 활용한 선형, 비선형 데이터를 분리 cost, gamma searching (0) | 2021.01.19 |
[DL] Pytorch 연구 모델 (0) | 2021.01.18 |
[ML] SVM을 활용한 데이터 분석 (0) | 2021.01.18 |
[seaborn] seaborn을 이용한 시각화 (0) | 2021.01.18 |