딥러닝에서의 양자화(Quantization) 이해하기

최근 딥러닝과 대규모 언어 모델(LLM)이 놀라운 성능을 보여주고 있지만, 이러한 모델들은 큰 계산 능력과 메모리를 필요로 한다는 도전과제가 있습니다. 특히 제한된 자원을 가진 환경에서는 이러한 모델들을 실행하기가 매우 어려울 수 있습니다. 이러한 문제를 해결하기 위한 핵심 기술 중 하나가 바로 '양자화(Quantization)'입니다.

들어가며

최근 딥러닝과 대규모 언어 모델(LLM)이 놀라운 성능을 보여주고 있지만, 이러한 모델들은 큰 계산 능력과 메모리를 필요로 한다는 도전과제가 있습니다. 특히 제한된 자원을 가진 환경에서는 이러한 모델들을 실행하기가 매우 어려울 수 있습니다. 이러한 문제를 해결하기 위한 핵심 기술 중 하나가 바로 ‘양자화(Quantization)’입니다.

양자화란 무엇인가?

양자화는 모델의 크기를 줄이면서도 성능을 최대한 유지하는 최적화 기법입니다. 모델의 파라미터와 데이터 타입의 정밀도를 조정함으로써, 모델을 더 가볍고 빠르게 만들어 더 많은 환경에서 적은 에너지로 실행할 수 있게 합니다.

모델 크기 계산
Copy모델 크기 = 파라미터 수 × 데이터 타입 정밀도

예를 들어, BLOOM과 같은 1,760억 개의 파라미터를 가진 모델의 경우:

  • float32 사용 시: 176B × 4 bytes = 704GB
  • float16 사용 시: 176B × 2 bytes = 352GB
  • int8 사용 시: 176B × 1 byte = 176GB

양자화가 필요한 이유

  1. 효율성: 부동소수점에서 정수로의 변환을 통해 계산 속도가 크게 향상됩니다.
  2. 메모리 절약: 더 적은 비트를 사용함으로써 모델 크기가 대폭 감소합니다.
  3. 에너지 소비 감소: 작은 모델 크기는 더 적은 계산 능력을 필요로 합니다.
  4. 배포 용이성: 스마트폰이나 임베디드 시스템과 같은 제한된 환경에서도 모델 실행이 가능해집니다.

양자화의 주요 방식

1. 학습 후 정적 양자화 (Post-Training Static Quantization, PTQ)

정의:

학습된 모델에 대해 가중치와 활성화를 양자화하는 방법입니다. 이 방법은 훈련을 마친 후 별도의 추가 학습 없이 모델을 양자화하는 방식입니다.

특징:
  • 간단하고 빠른 구현: 이미 학습된 모델에 대해 양자화만 수행하면 되므로, 구현이 매우 간단하고 빠릅니다.
  • 성능 저하 가능성: 모델이 양자화된 후, 정확도나 성능이 떨어질 수 있습니다. 특히, 양자화 과정에서 모델의 연산 정밀도가 낮아져, 수치적으로 손실이 발생할 수 있습니다.
  • 보정 데이터 필요: 양자화된 모델이 좋은 성능을 내도록 하기 위해, 보정 데이터(calibration data)가 필요합니다. 이 데이터는 모델의 활성화 값에 대해 적절한 양자화 파라미터를 계산하는 데 사용됩니다.
장점:
  • 구현이 간단하고, 학습 후 바로 적용할 수 있어 효율적입니다.
  • 모델 크기를 크게 줄일 수 있고, 실행 속도가 빨라질 수 있습니다.
단점:
  • 성능이 떨어질 수 있으며, 특히 활성화 값이 작은 모델에서는 성능 저하가 심할 수 있습니다.
  • 보정 데이터가 적절히 준비되지 않으면, 양자화된 모델이 원래 모델보다 성능이 떨어질 수 있습니다.
예시:
  • 가중치 양자화: 모델의 가중치를 32비트 부동소수점에서 8비트 정수로 변환합니다.
  • 활성화 양자화: 모델의 각 층의 활성화 값들도 32비트에서 8비트로 변환됩니다.
사용 사례:
  • 모바일 디바이스나 임베디드 시스템에서 모델 크기와 속도가 중요한 경우 사용됩니다.
  • 빠른 배포와 테스트가 필요한 경우에 유용합니다.

2. 동적 양자화 (Dynamic Quantization)

정의:

가중치만 양자화하고, 활성화는 실행 시 동적으로 처리하는 방법입니다. 이 방식에서는 모델 실행 중 활성화 값을 실시간으로 처리하며, 양자화된 가중치만 미리 준비됩니다.

특징:
  • 가중치 양자화: 모델의 가중치는 미리 양자화됩니다. 이로 인해 모델의 크기를 줄일 수 있고, 실행 속도도 빨라집니다.
  • 활성화 동적 처리: 활성화 값은 모델 실행 시 각 배치마다 동적으로 계산됩니다. 즉, 모델 실행 시에 활성화 값이 실시간으로 계산되고, 해당 값에 따라 양자화된 가중치와 함께 연산이 이루어집니다.
  • 실행 속도 저하: 활성화를 동적으로 처리하므로, PTQ 방식보다는 약간 느릴 수 있습니다. 하지만 여전히 동적 양자화는 효율적입니다.
장점:
  • 쉽고 빠른 구현: 가중치 양자화만 수행하고, 활성화는 런타임에서 처리하므로 간단한 구현이 가능합니다.
  • 다양한 입력 처리: 다양한 입력에 대해 유연하게 처리할 수 있습니다. 활성화 값을 실시간으로 처리하기 때문에 고정된 데이터셋이 아닌 실시간 데이터에서도 잘 작동합니다.
단점:
  • 속도 저하: 양자화된 가중치만 사용하고 활성화 값은 동적으로 처리되므로, PTQ 방식에 비해 실행 속도가 약간 느릴 수 있습니다.
  • 제약된 하드웨어 효율성: 하드웨어가 양자화된 활성화 값을 최적화할 수 없다면, 성능이 다소 제한될 수 있습니다.
사용 사례:
  • 주로 딥러닝 모델이 CPU에서 실행될 때 유용합니다. 가속 하드웨어(예: TPU)에서는 동적 양자화의 효과가 다소 제한적일 수 있지만, CPU 기반에서 실시간 데이터 처리가 필요한 경우 적합합니다.

3. 양자화 인식 학습 (Quantization-Aware Training, QAT)

정의:

양자화 인식 학습(QAT)은 학습 과정에서 양자화를 고려하여 훈련을 수행하는 방법입니다. 즉, 모델을 학습할 때부터 양자화된 값들이 적용되도록 설계하고, 이를 통해 양자화가 모델 성능에 미치는 영향을 줄입니다.

특징:
  • 양자화 인식: 훈련 과정에서 양자화를 인식하고, 그로 인한 성능 손실을 최소화하기 위해 가중치와 활성화에 대한 양자화의 영향을 학습합니다.
  • 학습 중 양자화: QAT는 학습 중에 양자화 오류를 보정하고, 양자화된 가중치와 활성화가 정상적으로 작동할 수 있도록 모델을 훈련합니다. 모델이 양자화된 상태에서 훈련되기 때문에 성능 저하를 줄일 수 있습니다.
  • 최고의 성능 유지: 양자화가 모델 성능에 미치는 부정적인 영향을 최소화하므로, 양자화 후에도 원본 모델에 가까운 성능을 유지할 수 있습니다.
장점:
  • 성능 유지: 양자화 후에도 모델 성능이 거의 그대로 유지됩니다. 특히, QAT를 통해 성능 저하를 최소화할 수 있습니다.
  • 다양한 하드웨어 최적화: QAT는 하드웨어에 최적화된 양자화 모델을 학습할 수 있어, 특정 하드웨어에서 최상의 성능을 발휘할 수 있습니다.
  • 높은 정확도: 양자화가 학습 과정에서 고려되므로, PTQ와 동적 양자화보다 더 나은 정확도를 제공합니다.
단점:
  • 복잡한 구현: 학습 과정에 양자화를 통합해야 하므로 구현이 상대적으로 복잡하고 시간이 오래 걸립니다.
  • 긴 학습 시간: QAT는 일반적인 학습에 비해 추가적인 학습 단계가 필요하므로 시간이 더 많이 소요됩니다.
  • 특정 레이어에 최적화 필요: 일부 모델은 특정 레이어에서 양자화를 잘 처리하지 못할 수 있기 때문에, QAT를 적용하기 전 모델에 대한 최적화가 필요할 수 있습니다.
사용 사례:
  • 고성능 시스템에서 양자화 후에도 성능 저하를 최소화하려는 경우, 예를 들어, 자율주행차, 로보틱스, 고속 이미지/비디오 처리 등 성능이 중요한 작업에서 많이 사용됩니다.
  • 또한, 엣지 디바이스AI 하드웨어에 배포되는 모델에서는 성능 저하 없이 양자화를 적용하는 것이 매우 중요할 때 유용합니다.

비교 요약

방법설명장점단점사용 사례
학습 후 정적 양자화 (PTQ)학습 후 모델의 가중치와 활성화를 양자화구현이 간단하고 빠름, 모델 크기 줄임, 실행 속도 향상성능 저하 가능성, 보정 데이터 필요모델 배포가 빠르게 필요할 때
동적 양자화학습 후 가중치만 양자화하고 활성화는 실행 시 동적으로 처리다양한 입력 처리 가능, 구현 간단실행 속도 약간 느림, 하드웨어 최적화가 어려울 수 있음CPU 기반 시스템에서 실시간 데이터 처리
양자화 인식 학습 (QAT)학습 중 양자화 고려하여 훈련최고의 성능 유지 가능, 하드웨어 최적화구현 복잡, 긴 학습 시간 필요고성능 요구 시스템, 엣지 디바이스 배포

PyTorch를 이용한 실제 구현 예제

아래는 MobileNetV2 모델을 양자화하는 간단한 예제입니다:

import torch
import torch.nn as nn
import torch.quantization
from torchvision import models, datasets, transforms
from torch.utils.data import DataLoader

# 1. MobileNetV2 모델 로드 및 준비
model = models.mobilenet_v2(pretrained=True)  # 미리 학습된 MobileNetV2 모델
model.eval()  # 모델을 평가 모드로 설정

# 2. 양자화 설정
# 양자화 설정은 기본 설정을 사용
model.qconfig = torch.quantization.default_qconfig  # 기본 양자화 설정 (float32 -> int8)
torch.quantization.prepare(model, inplace=True)  # 모델에 양자화 준비 작업을 적용

# 3. 데이터 로드 및 전처리
# 모델을 보정하기 위해 데이터 로더를 준비합니다.
# MNIST 데이터셋을 예로 들지만, 실제로는 다른 데이터셋을 사용할 수 있습니다.
transform = transforms.Compose([
    transforms.Resize(256),
    transforms.CenterCrop(224),
    transforms.ToTensor(),
    transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225]),
])

# 여기서는 예시로 ImageNet 데이터셋을 사용할 수 있습니다.
calibration_data = datasets.CIFAR10(root='./data', train=True, download=True, transform=transform)
calibration_dataloader = DataLoader(calibration_data, batch_size=32, shuffle=True)

# 4. 보정 데이터로 양자화 파라미터 결정
# 양자화를 위한 보정 데이터로 모델을 실행하여 양자화 파라미터를 결정합니다.
with torch.no_grad():
    for batch in calibration_dataloader:
        inputs, labels = batch
        # 모델을 배치에 대해 실행 (양자화 파라미터를 추정)
        model(inputs)

# 5. 모델 변환: 양자화된 모델로 변환
quantized_model = torch.quantization.convert(model, inplace=True)  # 모델을 양자화된 모델로 변환

# 6. 변환된 양자화 모델을 확인
print(quantized_model)

# 7. 모델 성능 평가
# 양자화된 모델을 평가하여 성능을 확인합니다. 예를 들어, 정확도를 계산할 수 있습니다.
def evaluate(model, dataloader):
    model.eval()
    correct = 0
    total = 0
    with torch.no_grad():
        for inputs, labels in dataloader:
            outputs = model(inputs)
            _, predicted = torch.max(outputs, 1)
            total += labels.size(0)
            correct += (predicted == labels).sum().item()
    accuracy = 100 * correct / total
    return accuracy

# 양자화 모델 성능 평가
accuracy = evaluate(quantized_model, calibration_dataloader)
print(f"Accuracy of the quantized model: {accuracy:.2f}%")

이 코드는 다음과 같은 과정을 거칩니다:

  1. 모델을 준비하고, 양자화에 필요한 설정을 추가합니다.
  2. 보정 데이터를 사용하여 양자화 파라미터를 계산합니다.
  3. 양자화된 모델로 변환합니다.

성능 비교 결과

실제 MobileNetV2 모델에 대한 양자화 적용 결과:

  • 원본 모델 크기: 8.9MB
  • 양자화 후 모델 크기: 2.35MB (약 4배 감소)
  • Top-1 및 Top-5 정확도: 원본과 거의 동일한 성능 유지

이 예제에서 볼 수 있듯, 양자화는 모델 크기를 대폭 줄이면서도 성능 손실을 최소화할 수 있는 방법입니다.

Ref. https://towardsdatascience.com/optimizing-deep-learning-models-with-weight-quantization-c786ffc6d6c1

양자화의 성능 비교

양자화 후 성능을 평가하는 것은 중요한 부분입니다. 양자화가 성능에 미치는 영향을 최소화하려면, 정확도를 유지하면서 모델을 얼마나 압축할 수 있는지를 평가해야 합니다.

모델 크기 변화

양자화를 통해 모델 크기는 크게 줄어듭니다. 예를 들어, BLOOM 모델과 같은 대형 모델의 경우, float32에서 int8로 양자화할 경우 모델 크기가 약 4배까지 감소할 수 있습니다. 이는 메모리와 디스크 공간을 절약하고, 서버나 클라우드 환경에서 모델을 더 효율적으로 운영할 수 있게 합니다.

성능 비교

양자화 후 성능은 모델의 종류와 적용된 양자화 방식에 따라 다를 수 있습니다. 하지만 Post-Training Static Quantization(PTQ) 방식에서는 성능 저하가 미미하거나 거의 없을 수 있으며, Dynamic Quantization이나 Quantization-Aware Training(QAT) 방식에서는 더 높은 성능을 유지할 수 있습니다.

양자화의 과제

양자화는 매우 유용한 기술이지만, 몇 가지 과제가 존재합니다:

  1. 성능 저하: 양자화는 모델의 정밀도를 낮추므로, 성능이 일부 저하될 수 있습니다. 특히 매우 세밀한 계산이 필요한 작업에서는 성능 저하가 눈에 띄게 발생할 수 있습니다.
  2. 양자화 전략 선택: 어떤 양자화 방식을 선택하느냐에 따라 성능과 효율성이 달라지므로, 적절한 양자화 방법을 선택하는 것이 중요합니다.
  3. 하드웨어 최적화: 양자화는 하드웨어의 지원을 받는 것이 중요합니다. 예를 들어, float16이나 int8을 지원하는 GPU나 TPU가 필요한 경우가 많습니다.

결론

양자화는 딥러닝 모델의 배포 및 효율성 최적화에 매우 중요한 기술입니다. 특히 제한된 리소스에서 모델을 운영해야 할 경우, 양자화를 통해 모델의 크기를 줄이고, 계산 속도를 개선하며, 메모리와 에너지 소비를 절감할 수 있습니다. Post-Training Static Quantization(PTQ) 방식은 구현이 간단하고 빠르며, Quantization-Aware Training(QAT) 방식은 성능을 최적화하는 데 유리하지만 더 많은 리소스를 요구합니다.

모바일, 임베디드 시스템 등 자원 제약이 있는 환경에서 AI 모델을 실행하려면 양자화는 꼭 고려해야 할 기술입니다. 이를 통해 더 많은 디바이스에서 고성능 AI 모델을 효율적으로 운영할 수 있을 것입니다.

댓글 남기기

이메일 주소는 공개되지 않습니다. 필수 필드는 *로 표시됩니다