논문리뷰

[논문리뷰] An Image is Worth 16x16 Words: Transformers for Image Recognition at Scale

syveany 2026. 2. 9. 17:23

이번에 대학원을 가게 되어서 논문과 친해져야 하므로
내 지식을 논문적인 느낌으로  파인튜닝 시키기 위해서 논문을 읽어보기로 했다.
 
하지만 전체를 다 읽을 자신은 없기에
일단 되는대로 주요 섹션(초록, 모델 설명, 피규어 등)들만 쏙쏙 뽑아서 읽어봤다.
 
(+ 읽으면서 의식의 흐름대로 쓸 것이기 때문에 중간중간 혼잣말을 할 수 있으니 양해 바람)
 

논문은 ViT논문!

https://openreview.net/pdf?id=YicbFdNTTy

내가 대충 알고 있던 ViT는.. 단어 그대로 Vision Transformer.
Transformer의 아이디어(순서 상관없이 어텐션 시키고 순서는 포지셔널 인코딩 시킴)를 비전에 적용한 모델이다.
기본 CNN은 그 네모격자를 사용해서 이미지를 순서대로 팡팡팡 치면서 읽어서 굉장히 느린데
이미지를 잘게 잘라서 한줄로 쫙 늘어놓은 다음에 positional encoding을 시키는 방법을 사용하면 성능이 훨 좋아진다.
암튼 transformer의 아이디어를 비전에 사용한 논문이라는 고런 깊은 의의가 있다!정도로 알고 있었다.
 
이렇게 대충 야매로 알고 있는 상태로 시작~
 

 

먼저 초록이다.

0. Abstract

트랜스포머가 nlp쪽에서는 표준이지만 아직 cv쪽에서는 적용을 많이 안 하고 있음

그냥 곁다리로 사용하거나 CNN의 일부 구조만 대체하는 정도임


하지만 그럴 필요가 없다! (띠용?)

CNN을 아예 안 쓰고 트랜스포머만으로도 성능 충분히 낼 수 있기 때문임. Image patch에 직접 트랜스포머 적용하면 됨


ViT모델을 큰 데이터셋에 pre-train 시키고 이미지 인식 벤치마크들(ImageNet, CIFAR-100, *VTAB)에 **transfer 했을 때 SOTA모델에 비해서 성능도 좋고 계산량도 적다다는 것을 확인함
 
*VTAB: Visual Task Adaptation Benchmark. 다른 태스크 이미지 검증하기 위한 데이터셋
        ImageNet하고 CIFAR는 같은 종류의 분류문제인데 VTAB는 다른 태스크에서도 잘 되는지 체크하는 데이터셋임
 
**Transfer하다: A 데이터셋으로 학습시킨 모델을 B 데이터셋에서 재사용하는 것
        보통 큰 데이터셋으로 pre-train -> 작은 데이터셋으로 파인튜닝
        이때 백본(인코더)은 유지하고 마지막에 분류하는 부분만 교체하는거임
        CNN은 작은 데이터셋에서도 잘 되지만 ViT는 큰 데이터셋+transfer 일 때 성능이 자 나옴
        단, 데이터가 너무 다르면 성능 확 떨어짐

 

그럼 이미지에 어케 트랜스포머를 어케 적용했는지 함 살펴보자
(라고 하면서 갑자기 섹션3으로 건너뛰기)

3. Method

모델은 트랜스포머 구조랑 최대한 비슷하게 구성했음. 비전에 맞게 뜯어고치지는 않음
 

3.1 Vision Transformer (ViT)

모델 전체 구조는 아래처럼 생김

(처음엔 걍 긍갑다 했는데 설명 보고 다시 돌아와서 보니 이해가 훨씬 수월하다..)

트랜스포머는 입력으로 1차원만 받으므로
2차원 이미지를 처리하기 위해서는 $x \in \mathbb R^{H \times W \times C}$ 크기의 이미지를 $x_p \in \mathbb R^{N \times P^2C}$로 flatten시켜야 함

표기상 주의점!

그냥 $HWC$라고 쓰면 숫자 하나처럼 보임! $H \times W \times C$ 이렇게 써야 차원처럼 보이는거임 


$H, W$: 원본 이미지 크기, $C$: 채널수, $P$: 이미지 패치 크기, $N = \frac{HW}{P^2}$: 패치 개수, 즉 입력 시퀀스 길이
라고는 하는데 수식으로 보니 와닿지가 않아서 직접 그려봤더니 별 내용은 아니었음

 

아래처럼 4*4*3 이미지에서 $P=2$라고 설정하고 잘라봤더니 $N = \frac{HW}{P^2} = \frac{16}{4} = 4$ 되면서 입력이 4개라는 것이 딱 보임

RGB있으면 RGB들도 다 flatten됨

RGB 하나하나 다 쓰다가 중간에는 생략햇습니다..

 

Flatten 시킨 다음 무엇을 하냐!

선형변환으로 $P^2C$를 *D로 맞춰줘야 함 (∵ 트랜스포머는 모든 레이어에서 $D$차원 잠재벡터를 사용하기 때문임)
이렇게 하는걸 patch embedding이라고 부름
* D: 모델에 따라 다름. ViT-Base는 $D$=768, ViT-Large는 $D$=1024, ViT-Huge는 $D$=1280임
 
BERT가 문장 전체를 대표하는 CLS 토큰을 맨 앞에 두는 것처럼 ViT도 CLS 토큰을 사용함
[CLS] patch1 patch2 patch3 ... patchN  형식임
 
그리고 이 CLS토근은 learnable 함. 학습과정에서 업데이트 되면서 점점 그 묶음을 대표하게 됨

 

앞에 CLS토큰 하나 넣은채로 레이어 거치면서 쫌쫌따리 서로를 보게 되고
결국 마지막 CLS토큰인 ${z_L}^0$이 모든 정보를 담게 되어서 얘만보고 분류 진행한다는 뜻임
 
(+ 지피티 설명 그대로 가져오는거 별로 안좋아하는데 너무 이해하기 쉽게 설명해줘서 나중에 다시 보려고 들고왔습니다..)

 
Pre-training 단계에서는 MLP(선형+활성화함수+선형) 쓰고 파인튜닝 단계에서는 선형 1개로만 분류함
(∵ Pre-training 때 데이터가 더 많기도 하고 학습 단계이기 때문. 파인튜닝은 비교적 데이터가 적으므로 선형 1개만 써서 분류해도 됨)
 

그러고 이러한 patch embedding 위에 *1차원 positional embedding도 같이 해서 인코더 입력으로 넣음

* 왜 1차원? -> 2차원 구조 고려한 복잡한 임베딩 해봤자 성능향상 없었다고 함

 

인코더 구조는는 transformer처럼 (LN -> MSA -> Residual -> LN -> MLP -> Residual ) * $L$ 꼴임

 
Inductive bias.

귀납적 편향.. 즉 선입견의 유무 측면에서 CNN하고 ViT의 차이를 설명해주고 있음

CNN은

- locality(가까운 픽셀끼리 의미가 있음)

- 2D구조(이웃간 관계가 중요함)

- trainslation equivariance(조금 움직여도 같은 물체임)이라는 가정을 함

 

근데 ViT는 이런거 없음!

걍 커널로 팡팡팡 치면서 가는거랑(CNN) 한줄로 쭉 늘어놓고 가는거(ViT)의 차이를 생각하면 쉬운 듯

 

그래서 데이터가 적은 상태에서는 CNN이 ViT보다 잘 됨. 근데 CNN의 가정이 안 적용되는 task에서는 ViT가 나음
 
Hybrid Architecture.

원본 이미지를 넣는 대신 CNN에서 feature map을 추출해서 넣을 수도 있음

이때도 CLS토큰하고 positional embedding은 동일하게 넣음

(CoAt모델인가 했는데 아니엇음. CoAt는 모델 전체에 섞는거고 얘는 그냥 입력만 섞는거)

 

3.2 Fine-Tuning and Higher Resolution

보통은 ViT를 대형 데이터셋에 pre-train 시키고 조그마한 downstream task에 파인튜닝 함

이때 downstream task의 클래스 수를 $K$로 둠

 

근데 그 앞에서 pre-train할 때 차원 크기가 $D$라고 했잖슴?

그래서 pre-train 단계의 예측 헤드를 제거하고 가중치 행렬의 크기가 $D*K$인 feedforward 레이어를 0으로 초기화시켜서 붙여서 예측 클래스가 $K$개가 될 수 있도록 만듦

 

이때, pre-train 단계보다 더 높은 해상도에서 파인튜닝하는 것이 성능향상에 도움이 됨

(∵ 걍 직관적으로 이해해보자면 pre-training 할 때는 계산량이 많으니까 낮은 해상도로 했다면

파인튜닝 단계에서는 비교적 데이터가 적으므로 해상도를 올릴 여유가 생기는 거임)


근데 이렇게 높은 해상도를 쓸 때도 패치 크기가 그대로이기 때문에 시퀀스 길이가 길어지게 됨

시퀀스 길이가 길어지는건 문제가 안되는데 이에 따른 positional encoding이 꼬이게 되어서

이를 해결하기 위해 *2D interpolation을 사용함

 

*2D interpolation: 2차원 보간. 걍 말그대로 2차원에서 보간하는거임

 인풋이 1D인데 2D 보간을 하는 이유: 의미가 2D이기 때문.1D 상태로 보간하면 의미가 깨짐

 1D로 했던걸 다시 2D로 돌려서 보간한 다음에 1D로 flatten 시킴

 

이 때 유일하게 inductive bias가 발생함!

(∵ 2D 보간 자체가 2D구조를 가정하기 때문) 

 


 
++ 여기까지만 정리하려고 하다가 Figure9가 신기하게 생겨서 뭔지나 함 봤음
 

Figure9: Position embeddings of models trained with different hyperparameters

 

그림은 학습된 position embedding들끼리의 코사인유사도를 시각화 한 거임

ViT-L16을 사용함. 즉, 16*16으로 잘라서14*14 개 패치가 나옴 (+ 이미지 크기는 224*224임을 알 수 있음)

확대해서 보면 각각의 패치가 조각조각 잘려있는데, 특정 패치가 다른 패치하고 얼마나 나타낸거임

예를 들어서 왼쪽 맨 아래 패치는 14행1열의 패치가 다른 패치들과 얼마나 유사한지 보여준거임

가까운 위치끼리 유사도가 높게 나오고 멀어질수록 유사도가 낮게 나오는 경향을 보여주기 위한 피규어였음

학습이 잘 진행되면서 점점 더 선명해지는 것을 알 수 있음

 

각각 그림을 보자면 아래와 같음

1번째 그림: 7에폭에 LR 0.0002 → 대충 보이기는 하는데 잘 안보임

2번째 그림: 7에폭에 LR 0.0004 → LR을 높였더니 학습이 더 잘 진행된 것을 확인할 수 있음. 경향이 더 선명하게 보임

3번째 그림: 14에폭에 LR 0.0004 → 에폭을 늘렸더니 경향이 더더 선명하게 보임

 

 

---

 

흐어 뇌에 힘주고 한줄한줄 읽었더니 대충 큰 그림은 잡은 것 같다.

근데 진빠져서 하루에 하나 이상은 못 읽겠다.. 암튼 재밌다.

다음에는 여기서 파생된 transformer들을 쭈르륵 정리해보려고 한다.

 

끝~