논문 리뷰, 구현

7. DenseNet 논문 리뷰,구현

jwjwvison 2022. 7. 3. 15:55

 이번 포스팅에서는 Densely Connected Convolutional Networks논문에 소개된 DenseNet에 대해서 리뷰해 보겠다.

 

Abstract

 최근의 연구 결과에 따르면, 입력에 가까운 계층과 출력에 가까운 계층 간의 짧은 연결이 포함될 경우, 컨볼루션 네트워크가 훨씬 더 깊고, 정확하며, 훈련에 효율적일 수 있다. 이 논문 저자들은 이러한 관찰을 바탕으로 Dense Convolutional Network(Dense Net)을 소개할 것인데 이는 각각의 층을 모든 다른 층에 feed forward fashion 형태로 연결한 것이다.

 전통적인 합성곱 신경망은 L개의 층이 있으면 L개의 연결이 있다. 그러나 이들의 network는 L(L+1)/2 개의 직접 연결이 있다. 각각의 층에 대해 이전 층의 특성맵은 입력으로 사용되며 자체 특성맵은 이후의 모든 층에 대한 입력으로 사용된다.

 

 Dense Net은 설득력 있는 이점을 가지고 있다. vanishing-gradient 문제를 완화하고, feature 전파를 강화하며, 특성 재사용을 장려하고, 파라미터의 수를 크게 줄인다.

 

 DenseNet은 테스트에서 다른 SOTA 모델을 넘는 상당한 향상을 얻었고 이 모델은 적은 계산량으로 높은 성능을 낼 수 있다.

 

Introduction

 CNN의 깊이가 더 깊어지면서, 새로운 연구 문제가 발생했다. 이는 input이나 gradient가 많은 층을 통과하면서 이들이 사라질 수 있다는 문제이다. 최근 많은 연구들이 이 문제를 다루었다. ResNet 과 FractalNet은 이러한 문제를 다루었는데 이들의 공통점은 이전 층과 이후 층을 연결하는 short paths를 만들었다는 점이다.

 

 이 논문에서 논문의 저자들은 네트워크 층 간의 정보 흐름을 극대화하기 위해 모든 층(매칭되는 특성맵 크기)을 서로 직접 연결하는 단순한 연결 패턴에 대한 통찰력을 제공하는 구조를 제안했다. feed-forward 본질을 보존하기 위해, 각 층은 선행하는 층들로 부터 추가적인 inputs을 얻고, 자체 특성맵을 이후의 모든 층에 전달한다. 결정적으로 이들은 ResNet과는 다르게 feature가 층으로 전달되기 전에 합산을 통해 feature를 결합하지 않는다. 대신 concatenationg을 사용해서 연결한다. 그러므로 L번째 층의 특성맵은 이후 L-1개의 모든 층으로 통과한다. 이러한 과정으로 인해 L-layer network에는 전통적인 구조가 L개의 연결이 존재하는 반면 여기서는 (L(L+1)/2) 개의 연결이 존재하게 된다. 이러한 dense connectivity pattern 때문에 논문의 저자들은 이를 Dense Convolutional Network(DenseNet)이라고 지칭한다.

 

 이러한 조밀한 연결 패턴이 가져올 수 있는 효과는 중복 특성맵을 다시 학습할 필요가 없기 때문에 기존 컨볼루션 네트워크보다 적은 파라미터를 필요로 한다는 것이다. ResNet은 특성상 각 층마다 그들의 가중치가 존재하기 때문에 파라미터 수가 상당히 컸다.

 

 DenseNet의 층들은 매우 좁다(각각의 층은 12개의 필터가 존재한다). 적은 set의 특성맵을 네트워크의 'collective knowlegde'에 추가하고, 나머지 특성맵을 변하지 않게 하고 마지막 분류기가 netwrok에 있는 모든 특성맵을 바탕으로 결정을 내린다.

 

 파라미터 효율 이외에도 다른 장점이 있는데 이는 네트워크를 통한 정보와 gradient의 향상된 흐름이다. 이는 train하기 쉽게 만들어준다. 더군다나 논문의 저자들은 dense connection이 정규화 효과를 갖고 있다는 점을 관찰했는데 이것은 더 작은 trainig set에 대해 overfitting을 줄여준다.

 

Related Work

 Highway Network는 100개 이상의 계층이 있는 end to end network를 효과적으로 교육할 수 있는 수단을 제공한 최초의 아키텍쳐중 하나이다. bypassing path는 이러한 deep network훈련을 쉽게 만들어주는 주요 요인이라고 추측되어진다. 최근에는 확률적 깊이(stochastic depth)가 deep residual networks를 훈련중에 랜덤으로 층을 dropping하면서 훈련을 향상 시켰는데 이 stochastic depth는 1202개 층의 ResNet을 성공적으로 훈련시키기 위해 제안되었다.

 

 DenseNet은 매우 깊거나 광범위한 아키텍쳐에서 표현력을 끌어내는 대신 기능 재사용을 통해 네트워크의 잠재력을 활용하여 훈련하기 쉽고 매개변수 효율성이 높은 축약된 모델을 산출한다. 서로 다른 층에서 학습한 특성맵을 연결하면 후속 층 입력의 변동이 증가하고 효율성이 향상된다. 이점은 Dense Net과 ResNet 사이의 주요한 차이이다. 또한 Inception 모델보다 더 간단하고 더 효율적이다.

 

 

DenseNet

 컨볼루션 네트워크를 통해 전달되는 단일 이미지 x0를 고려하자. 네트워크는 각각 비선형 변환 H(')를 구현하는 L레이어로 구성되며, 여기서 레이어를 인덱싱한다. H(')는 배치 정규화(BN),ReLU, pooling 또는 Convolution과 같은 연산의 복합 함수일 수 있다. 우리는 'l번째 층'의 출력을 xl로 나타낸다.

 

 ResNet은 다음과 같은 식으로 표현될 수 있는데 identity function 과 output이 합해지기 때문에 이는 network의 정보 흐름을 방해할 수 있다.

 층 사이의 정보 흐름을 향상시키기 위해 저자들은 다른 연결 패턴을 제안했다. 이들은 어느 층으로부터 하위 모든 층까지 직접 연결을 소개했다. Figure 1은 이를 그림으로 설명한다.

 결과적으로 l번째 층은 선행하는 모든 층으로 부터 특성 맵을 받는다. 이는 다음과 같은 식으로 나타낼 수 있다.

 Composite function

  이들은 Hl(')을 세개의 연속된 수행을 하는 합성함수로 정의했는데 이는 BN,ReLU,3x3 convolution이다.

 

 Pooling layers

식(2)에서 사용되는 연결 작업은 특성맵의 크기가 변경되면 실행할 수 없다. 그러나 convolutional networks의 필수적인 부분은 down sampling층 인데, 이는 특성맵의 크기를 변환해준다. 이들의 구조에서 downsampling을 용이하게 하기 위해서 이들은 multiple densely connected dense blocks로 network를 나누었다. 이는 convolution과 pooling을 수행한다. 이들의 실험에서 사용한 transition층은 batch normalization 층과 1x1 convolutional layer 이후에 따라오는 2x2 average pooling 층으로 구성되어 있다.

 

 Growth rate

만약 Hl이 k개의 특성맵을 생성한다면 l번째 층은 k0 + k(l-1) input 특성맵을 가지고 k0는 input층의 채널의 수이다. DenseNet과 다른 network의 중요한 차이점은 DenseNet은 좁은 층을 가진다는 것이다(k=12). 이러한 이유는 각각의 층은 선행하는 특성맵에 대한 접근을 할수 있기 때문이다.

 

 Bottleneck layer

 각각의 층이 오직 k개의 output 특성맵을 만들어도 각각의 층은 일반적으로 더 많은 input을 받는다. 그러나 1x1 convolution을 통해 특성맵의 수를 줄일수 있고 이로인해 계산 효율을 향상시킬수 있다. 이 논문의 저자들은 특히 이들의 DenseNet에 효율적이라는 것을 발견했고 이들은 이 network를 Hl의 BN-ReLU-Conv(1x1)-BN-ReLU-Conv(3x3)버전이라고 지칭한다.

 

Implementation Details

 이 실험에서 사용된 DenseNet은 세개의 dense block를 사용했는데 이 dense block는 같은 수의 층을 가지고 있다. 첫번째 dense block에 들어가기 전에 output channel이 16개인 convolution이 입력 이미지에 수행된다.

 3x3 size의 필터를 갖는 합성곱층은 특성맵의 사이즈를 고정하기 위해 제로패딩 된다. 이들은 1x1 convolution과 2x2 average pooling을 하는 transition 층을 연속된 dense block들 사이에 사용했다.

 마지막 dense block에서는 global average pooling이 수행되고 softmax classifier가 그 뒤를 잇는다.

 세가지 dense block들에서 특성맵의 사이즈는 각각 32x32, 16x16, 8x8이다(CIFAR-10).

 

 

구현

def densenet(n_classes,filters=32):

  # batch norm + relu + conv
  def bn_rl_conv(x,filters,kernel=1,strides=1):

    x=BatchNormalization()(x)
    x=Activation(keras.activations.relu)(x)
    x=Conv2D(filters,kernel,strides=strides,padding='same')(x)
    return x

  def dense_block(x,repetition):  # 줄기를 기준으로 새로운 가지 형성, 새로운 가지만들고 array에 새로운 가지 만들때마다 넣어줌
    array=[x]
    for _ in range(repetition):
      y=bn_rl_conv(x,4*filters)
      y=bn_rl_conv(y,filters,3)
      array.append(y)
      x=concatenate(array)
    return x

  def transition_layer(x):
    x=Conv2D(12,(1,1),strides=2,padding='same')(x)
    x=AvgPool2D(2,strides=2,padding='same')(x)
    return x

  input=Input(shape=(224,224,3))
  x=Conv2D(64,7,strides=2,padding='same')(input)
  x=MaxPool2D(3,strides=2,padding='same')(x)

  for repetition in [6,12,24,16]:
    d=dense_block(x,repetition)
    x=transition_layer(d)
  
  x=GlobalAveragePooling2D()(d)
  output=Dense(10,activation='softmax')(x)

  model=Model(input,output)
  return model

model=densenet(10)
model.summary()