activation function이 왜 중요한가?
- 비선형성을 줘서 중요함
- activation을 안쓰면 레이어가 계속 중첩이되면 하나의 선형 형태로 구성이 되고 한번 레이어를 쌓는 것과 레이어를 여러개 쌓는것과 동일하게 됨
loss
- 주어진 데이터에대해 파라미터를 업데이트하는 펑션

퍼셉트론에서 학습
1. 파라미터 값을 초기화
2. 현재 위치에서 경사도를 계산
3. 기울기가 작아지는 방향으로 포지션을 이동
chain_rule
- 함수를 연결지어서 미분값을 계산
gradient descent 방법의 문제점
- 많은 학습 데이터가 필요함
- 에포크별로 미분 계산은 시간이 많이 걸림
- 최적화를 위해 많은 에포크가 필요되어짐
Convolutional Neural Network

컨볼루셔널 층 + 풀링 연산 + MLP(Fully-connected layers)
Pooling operation
- 이미지를 줄임
- 리셉티브 필드도 더 키움 => 픽쳐의 한 부분이 이미지의 많은 부분을 볼 수 있게 함
Pooling 종류
- Max pooling
- Average pooling
- L2-norm pooling
why pooling
- spatial invariance(이미지의 한 부분의 데이터 분포는 다른 부분에서의 데이터 분포와 다르지 않다)
위치가 변경되어도 max pooling은 값이 변하지 않으니까
- to abstract image information
이미지의 넓은 부분을 봄으로써 의미까지 캡쳐할 수 있어서
- 메모리 사용과 파라미터 수를 줄일 수 있어서

cnn 업데이트 할때마다 이미지를 보면 low layer에서는 엣지나 블럭을 캡쳐하고 있고
upper layer에서는 abstract한 핏쳐(사람 얼굴 또는 의미론적인 모양들)
미드 레벨에서는 패턴들을 자동적으로 학습하고 있는 것임
overfitting
- 훈련 데이터는 네트워크 파라미터 수보다 반드시 많아야함(근데 파라미터가 1억개면? 데이터 구하기도 어려울 것임)
일반화를 잘하기 위해서는(오버피팅이 안되고) 여러 트릭들이 있음
오버피팅을 피하기 위한 트릭
- Dropout
풀리커넥티드 레이어에서 특정 뉴런을 꺼주는 것임
추가적인 모델이 없어도 모델 앙상블 해주는 효과가 있음
앙상블: 예측을 여러개 해가지고 그것을 중첩시켜서 더해서 여러개의 모델의 효과를 같이 누리는 데이터 처리 기법
드롭 아웃만 통해서 그 여러개의 모델을 앙상블하는 효과를 낼 수 있다는 것
- Weight decay

에러 값을 넣어줄 때 에러의 웨이트가 어느 정도 이상으로 커지지 않게 그 웨이트의 제곱값을 최소화 해야하는 값을 넣어주는 것
모델의 가중치를 일정 비율로 감소시켜, 가중치 값들이 크게 증가하는 것을 제한
- Early stopping
에러가 밸리데이션 에러 또는 벨리데이션 에러가 가장 낮거나 정확도가 높은 부분에서 선택하는 얼리 스탑핑 기법 사용
기존 네트워크의 파라미터를 가져와서 파인튜닝하는 것도 모델 네트워크의 초기화로 좋은 기법임
CNN에서 필터와 가중치는 같은 의미고 학습을 하는 건 필터를 업데이트 하는 것임
그래서 그 특징을 뽑아내는 필터가 이미지내에서 특징을 가장 잘 뽑아내는 걸로 학습이되면
추론할때 잘 업데이트된 필터를 사용하면서 새로운 이미지에도 업데이트 된 필터가 특징을 잘 뽑을 수 있게 하는것

AlexNet
- ILSVRC 우승
- 7개 레이어
- conv-pool-LRN(local response normalization)-conv-pool-LRN-conv-conv-conv-pool-FC-FC-FC
- 알렉스넷은 11*11 컨볼루션 19개의 필터를 통과시켜서 한 번에 레졸루션 확 줄인다음 하이레벨 시메틱스를 인코딩
ZFNet
- 알렉스넷 하이퍼 파라미터 튜닝해서 나옴
VGG
- 좀 더 깊고 간단한 아키텍처
- 16, 19 layers
- LRN 없앰, 3*3 conv filters, 2*2 max-pooling and a few FC layers
- 알렉스넷과 달리 컨브레이어에 렐루가 붙고 이제 비선형 액티베이션이 생기고 컨브 층 두개를 통과시키면 리셉티브 필드가 더 커지니까 11by11 모듈을 넣지 않고 3*3 모듈을 넣음
- VGG 네트워크가 하드웨어에 좀 더 옵티마이즈 잘 되어있음
- 11*11를 96개 쓰는것보다 3*3을 여러개 쌓는것이 더 성능이 좋고 파라미터 수가 적다
GoogleNet
- 깊고 컴퓨터 연산이 효율적인 인셉션 모듈을 릴리즈
Resnet
- 레지듀얼 커넥션(=스킵커넥션) 기법을 사용해서 이전의 특징을 참조하고 그래디언트의 흐름이 계속 끝까지 전파 될 수 있게 함
- Depth가 중요한 요소인데 왜 중요하냐면 뎁스가 깊어질수록 리셉티브 필드가 커짐
- 그리고 깊어질 수록 논리니어 기능이 충족되기때문
- VGG 스타일을 따르는데 스킵 커넥션이 들어감
- 모든 레이어마다 학습을 좀 안정화시키기위해서 배치 정규화가 모든 컴브 뒤에 들어감
- 주기적으로 필터사이즈를 스트라이드 2에 컨브넷을 통과시켜서 사이즈를 줄여줌
- FC 레이어가 없음, 글로벌 에버리지 풀링만 가지고도 피쳐가 잘 학습이 될수 있기때문에 FC레이어를 없애버림, 드롭아웃도 없앰
- 그러면 어떻게 레즈넷이 잘 동작함?
스킵 커넥션의 장점이 레이어 하나만 통과했을때 예측하기 어려워지는 문제를 매우 깊은 네트워크에서 레지듀얼 커넥션을 통해 해결함
- 역전파가 베이직, 바틀넥 모듈에서 스킵 커넥션 모듈을 타고 통과해서 베니싱 그래디언트 문제를 막아줌
- 낮은 네트워크에서 앙상블 효과도 봄
- basic block
-- 3by3, skip connection
- bottleneck block
-- 1by1, skip connection
torchvision.resnet 링크
https://github.com/pytorch/vision/blob/main/torchvision/models/resnet.py
- resnet 쓰면서 성능 높이고 싶으면 wide_resnet을 백본으로 사용하기
**글로벌 에버리지 풀링과 완전 연결 계층이 좀 헷갈려서 정리
글로벌 에버리지 풀링
- 작동원리: 특징 맵의 각 채널에 대해 평균값을 계산, 각 채널의 모든 요소에 대한 평균을 취하여 하나의 숫자로 축소함 결과적으로 각 채널에서 하나의 평균값이 생성됨
- 목적: GAP의 주된 목적은 공간적 차원을 축소하여 특징맵의 크기를 감소시키는 것, 이 과정은 특징 맵 내의 공간적 정보를 요약하여 각 채널의 대표값을 제공
- 파라미터 없어서 학습이 안되고 이때문에 과적합의 위험을 줄여줌
- 활용: 주로 cnn 마지막 컨볼루션 레이어 다음에 사용되며, 클래스별 공간적 특징을 요약하여 분류 작업에 사용됨
완전 연결 계층(FC레이어)
- 작동원리: FC레이어는 입력을 받아 각 입력에대해 가중치를 곱하고 편향을 더함, 일반적인 신경망 레이어처럼 작동하고 모든 입력 노드가 모든 출력 노드와 연결됨
- 목절: FC 레이어의 목적은 학습된 고수준 특징을 기반으로 출력을 생성하는 것, 일반으로 cnn의 마지막에 위치하여 특징 맵을 클래스 점수나 예측값을 변환
- 파라미터 많음: FC레이어는 많은 수의 파라미터를 가짐, 각 연결마다 가중치가 있으며, 이는 모델의 크기를 크게 만들고 과적합을 유발할 수 있음
- 활용: FC레이어는 일반적으로 분류, 회귀 문제에서 출력 레이어로 사용됨, 또한 복잡한 패턴 인식이나 데이터 비선형 관계학습에 사용됨
DenseNet
- 2017년에 스킵 커넥션과 다른 커넥션을 포함해 덴스 채널의 컨캣으로 깊은 네트워크를 릴리즈
- add dense connection

- 더많은 skip connection, 그리고 channel wise concatenation을 함(더하는게 아니라 concat하면 정보가 보존되서 그래디언트 플로우 유지되고 스테이블하고 학습 가능)
SENet
- 채널 어텐션 기법을 통해서 딥 네트워크의 성능을 강화 시킴
- SENet은 SE 모듈처럼 다른 네트워크에 다 포함 될 수 있어서 혁신적임
- squeeze and Excitation module

- squeeze: 글로벌 에버리지 풀링을 사용해 피쳐맵의 공간 차원을 압축, 이로 인해 핏쳐맵의 각 채널에 해당하는 1차원 벡터 생성
- excitation: 위에서 압축한 벡터를 채널 간 의존성 계산 하는것, 어떤 피쳐맵이 중요하고 덜 중요한지 뎁스간에 가중치를 구하는 과정, 위의 C(채널)만큼 뎁스가 있으면 각각의 중요도를 color map으로 그려낸 것
- SE 모듈이라 어떤 네트워크에도 적용 가능함
- 연산 비용 약간 증가시켜도 퍼포먼스가 크게 향상되는 장점이 있음
EfficientNet

- Network Depth, Network Width, Input Resolution search
- baseline에 스케일링 한다는 것
- 뉴럴 아키텍처 서치를 하는데 알고리즘으로 돌리는게 아니라 그리드 서치를 해서 점점 키워나가는 방법
- width, depth, resolution 스케일링을 통해 컴파운드 스케일링을 한다는 것임
Efficient cnn
- 스몰모델 만드는 것이 목적(더적은 연산과 파라미터로 동일한 성능을 내는것)
- 고퀄의 아웃풋과 충분한 정보를 가진 피쳐맵을 뽑는것
- small neural network size, 일반적인 앱 사이즈는 100mb넘지 않기 때문에
- 연산의 오버헤드도 적어야함
그래서, Effiicient하게 만드는 법
1. improving operator design
- Depthwise-separable convolution
- shift-based convolution
2. improving architecture design
- residual structure
- inverted-residual structure
- squeeze-excitation module
3. applying optimization techniques
-low-precision computation
-prunig
-low rank approximation
SqueezeNet
전략1. 3*3필터를 1*1필터로 바꿔줌
- 3*3 필터는 분할된 3*3영역들을 슬라이딩 윈도우로 읽으면서 피쳐 추출을 함
근데 그걸 1*1로 바꿔도 사실 인풋, 아웃풋, 피처 해상도는 같아지니까
그래서, 위에 방법을 사용해서 9배 적은 파라미터 수를 줄였다고 함
전략2. 인풋의 채널 수를 줄임
- 필터의 갯수와 인풋 채널 수 를 줄임
*conv layer 파라미터 계산 공식
- (kernel) x (kernel) x (number of input channel) x (number of filter)
전략3. 컨볼루션 레이어의 액티베이션 맵을 뒤쪽으로 보냄
- 앞에서 줄어든 파라미터 수많큼 손실이 있을 텐데 피쳐 해상도를 키우면서 피드포워딩해서 더 좋은 표현력을 얻음
- 분류 정확도에 조금더 기여할 수 있게됨
(함정있음) 모델 파라미터 수는 줄지만 실제로 동등하게 모델 사이즈를 줄이면 연산 수는 어쨋든 더 줄어드는데 오히려 연산 수가 늘어날 수도 있음

class Fire(nn.Module):
def __init__(self, inplanes: int, squeeze_planes: int, expand1x1_planes: int, expand3x3_planes: int) -> None:
super().__init__()
self.inplanes = inplanes
self.squeeze = nn.Conv2d(inplanes, squeeze_planes, kernel_size=1)
self.squeeze_activation = nn.ReLU(inplace=True)
self.expand1x1 = nn.Conv2d(squeeze_planes, expand1x1_planes, kernel_size=1)
self.expand1x1_activation = nn.ReLU(inplace=True)
self.expand3x3 = nn.Conv2d(squeeze_planes, expand3x3_planes, kernel_size=3, padding=1)
self.expand3x3_activation = nn.ReLU(inplace=True)
def forward(self, x: torch.Tensor) -> torch.Tensor:
x = self.squeeze_activation(self.squeeze(x))
return torch.cat(
[self.expand1x1_activation(self.expand1x1(x)), self.expand3x3_activation(self.expand3x3(x))], 1
)
파이토치 Fire 클래스임
self.squeeze = nn.Conv2d(inplanes, squeeze_planes, kernel_size=1)
self.squeeze_activation = nn.ReLU(inplace=True)
=> 스퀴즈 모듈이 1*1 컨브를 통과 시키고
self.expand1x1 = nn.Conv2d(squeeze_planes, expand1x1_planes, kernel_size=1)
self.expand1x1_activation = nn.ReLU(inplace=True)
self.expand3x3 = nn.Conv2d(squeeze_planes, expand3x3_planes, kernel_size=3, padding=1)
self.expand3x3_activation = nn.ReLU(inplace=True)
torch.cat(
[self.expand1x1_activation(self.expand1x1(x)), self.expand3x3_activation(self.expand3x3(x))], 1
)
=> expand 모듈에서 1*1과 3*3을 중첩 시켜가지고 익스팬드를 해서 concat해줌

shift operation-Spatial Convolution May Not Necessary
- motivation: spatial 컨브가 필요하지 않을 수 있다
- spatial conv: 3*3 필터가 한 채널과 어떤 스파셜 레졸루션을 쭉 긁어가지고 읽음 한번만 진행한다고 보면 그걸 읽고 써메이션함
- 써메이션을 해버리니까 그 채널을 쉬프팅해가지고 읽어도 그게 다 써메이션 되는 정보면 그 위치들에 대해서 유지만 되면 되지 않느냐는 의미
- Basic idea: replace spatial convolution by shift operation and only rely on 1*1 convolution for feature extraction
(쉬프트 오퍼레이션을 통해 스파셜 컴볼루션을 리플레이스 하자임, 그러면 1*1 컨브만 사용해도 피처 추출이 충분하다
충분히 지역적인 정보도 인코딩이 되면서도 성능을 낼 수 있다가 핵심 아이디어)

shift is Efficient
- 하드웨어가 이런 쉬프트 오퍼레이션에 최적화가 되어있음
- SIMD pipeline, systolic array
- 하이 디멘션 오퍼레이션이 핸들하기 어려움
- Data duplication, replacement is required
- shift operation이면, spatial operation이 불필요하다
- high order 텐서 핸들링을 위한 하드웨어 서킷을 최소화 할 수 있음
shift 정리
- 어떤 피처맵의 하나의 채널에서 그걸 전후 좌우로 이동시키는 shift를 통해서 지역적 정보도 한 피처 포인트에서 읽어주고 그걸 인코딩해주는 기법
Active Shift
- shift 기법을 active shift로 바꿔준 거임, 모든 방향으로 움직일 수 있고 꼭 정수값으로 방향이 이동하는 것이 아님
- shift: memory access를 줄이기 위해, spatial convolution을 deconstruction함
- active shift: 1) depthwise shift 2) shift parameters를 추가 3) Non-integer shift
- 문제: 비선형 인터폴레이션 때문에 부자연스럽게 이행됨
무슨말이냐면 active shift는 실수값을 움직이게 되면 대각선으로 0.15의 위치로 이동하면 어떤 값을 넣어야할지 모르니까
그러면, interpolation을 해야하는데 이게 연산량이 커서 구현적으로 말이 안될 수 있음
active shift 정리
- 채널별로 다른 쉬프트를 사용
- 채널머더 새로운 쉬프트를 도입했음
- interpolation을 사용해서 비선형 쉬프트로 확장할 수 있었음
All you need is a Few shifts: Designing Efficient Convolutional Neural Networks for image classification
- interpolation때문에 연산이 오래 걸리던 것을 round 연산을 통해 깎았고
- straight-through Estimation으로 이제 Gradient Approximation을 해서 좀 더 학습 시간을 줄였음
sin함수같은걸 통해서 부호만 보고 이제 연산을 할 수 있게 한다던지
- L1 regularization을 통해서 sparsity를 보장함
MobileNet-v1
- Depthwise-separable convolution(각 채널에 대한 서로다른 컨볼루션 진행)
- Conventional full-convolution covers entire channels across receptive field input
- Some feature maps are redundant & highly correlated
- Do we need all channels?
- Decoupling channel-wise feature extractor & spatial feature extractor
- Depthwise Conv: channel-wise weights
- Separable Conv: 1*1 convolution

위의 이미지에서 세번째는 pointwise convolution임(1*1 컨볼루션을 말함)
1*1 컨볼루션이 여전히 비용이 비싸다고 느끼는 사람이 있었음

오버헤드를 최소화할 수 있을것이라고 생각=> shuffle net
ShuffleNet
- 그룹 컨볼루션 구조를 사용함
- depthwise-separable convolution은 채널간에 정보교환이 없음

shufflenet은 첫번째 그룹에 대한 채널을 첫번째에 넣고 두번째 그룹에대한 채널은 두번째에 넣고 그런식으로함

- 1*1 conv가 그룹컨볼루션과 셔플이 포함된 형태로 바뀜
- relu는 DW 이후에 적용되지 않음
- element-wise addition을 채널을 키워서 컨캣하는 구조로 바뀜

Batch Normalization
- 배치 놈이 잘되는 이유
최적화 공간을 상당히 부드럽게 만들어줌
로스 기울기를 안정적이고 더 예측 가능하게 해줌
러닝레이트를 더크게 할 수 있게됨(로컬미니마 안걸리고 평평한 곳에서도 운영됨)
훈련을 상당히 빠르고 덜 민감하게 만들어줌
- 각 미니배치에서 노멀라이즈를 해주고
- 학습이 더 빨리 수렴되도록 함
- 초기화에 덜 민감함
- 정규화를 줌
- 미니 배치 기준 0~1사이의 값을 가지게 만들어주는 것
mobilenet-v2

- movilenet v1 에서는 depth wise conv와 residual block의 문제는 activation values(네트워크에서 활성화 함수를 거친값)작아지는 것인데 액티베이션의 채널값을 유지할 수 없는지 고민했음
- feature extractor의 spatial compacity가 충분하지 못함
그래서, mobilenet-v2에서 제안하는 것은 inverted residual module
- 왼쪽은 기존 depth wise+residual이고 채널이 많은걸을 1*1로 줄이고 줄인걸 다시 더하기 위해 채널을 키웠고
오른쪽이 핏쳐의 채널을 다시 키우고 피드포워딩을 하고 다시 줄여주는 형태임
- relu와 information lost

- 피쳐맵이 저차원 공간으로 임베딩됬을때 정보 손실 없이 차원을 줄임
- 렐루를 사용하지않고 렐루를 업데이트한 렐루6를 사용함
MobileNet-v3
- 새로운 비선형 활성화 함수:: h-swish
- squeeze-excitation module
- 자동화된 아키텍쳐 튜닝

0인 부분에서 그래디언트가 확 사라지지 않음
Vision Transformer
- 멀티헤드 어텐션을 사용해서 여러개의 채널을 쌓고 컨볼루션보다 더 넓은 영역을 볼 수 있는 컨볼루션의 지역성이라는 인덕티브 바이어스를 제거하고 모델을 구성하는 구조
- 셀프어텐션
- 트랜스포머 구조
- 이미지를 패치로 나누고 리니어 프로젝션 시켜서 원바이원 컨볼루션을 통과시켜서 어떤 패치 임베딩을 만들고 그걸 트랜스포머 인코더에 통과시킴
'Study 공부할레나' 카테고리의 다른 글
| [컴퓨터비전 정주행 Kit] Part2 ch05 객체탐지와 분할 (0) | 2024.03.18 |
|---|---|
| [컴퓨터비전 정주행 Kit] Part2 ch04 표현학습 (2) | 2024.01.27 |
| [컴퓨터비전 정주행 Kit] Part2 ch02 (1) | 2023.12.18 |
| [컴퓨터비전 정주행 Kit] Part2 ch01 (0) | 2023.12.16 |
| [컴퓨터비전 정주행 Kit] Part1 ch1 (1) | 2023.12.09 |