연산을 효율적으로 하기 위해 float에서 연산하는 것이 아닌 integer 연산을 합니다. 대신 정확도는 줄어듭니다
$r = S(q-z)$
q: quantized fixed-point value (integer)
r: real float-point value
S: scale (float)
Z: zero-point (bias)
어느 모델의 weight가 다음과 같은 분포를 하고 있다고 가정해봅시다
-2 | -1 | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 |
그리고 3비트로 아래의 수를 나타내고 싶다고 가정해봅시다.(uint3)
uint3의 범위는 0($ \alpha_q $)~7($ \beta_q $)입니다
위 weight의 범위는 -2($ \alpha $)~14($ \beta $)입니다
총 16의 범위를 가진 숫자를 7의 범위를 가진 숫자로 표현해야합니다
따라서, $S = \frac{\beta- \alpha}{\beta_q- \alpha_q}$=2.3
zero point는 중간값을 표현합니다
quantization후의 중간값과 quantization하기전의 중간값이 같아야 합니다
$\frac{\alpha+\beta}{2}$ 가 $\frac{\alpha_q+ \beta_q }{2}$를 표현해야하므로,
$S(\frac{\alpha_q+ \beta_q }{2}-z) = \frac{\alpha+ \beta }{2}$
S는 위에서 이미 구했습니다. z를 uint로 표현하기로 했으므로 정리해서 round를 씌워주면
$z=round(\frac{\beta \alpha_q-\alpha \beta_q}{\beta - \alpha})$=1
이제 아래와 같은 방법으로 quantization을 수행할 수 있습니다
$q = round(\frac{x}{s})+z$
아래와 같이 변경됩니다
0 | 1 | 1 | 1 | 2 | 2 | 3 | 3 | 4 | 4 | 5 | 5 | 5 | 6 | 6 | 7 | 7 |
$\alpha$와 $\beta$를 min/max로 구했지만,
outlier가 있으면 정확도가 깨질수 있어 상위 1%값 및 99%의 값으로 잡고 범위 밖의 값은 clamp하는 방법도 있습니다
Post-Training quantization
pretrained된 모델에 quantization을 적용합니다
convolution layer에서 MAC(Multiply–accumulate)가 일어나서 uint32까지 있어야 숫자 표현이 가능합니다
(uint8 * uint8 = uint16이고 uint16 덧셈이 여러번 일어납니다)
weight는 model이 학습되고 나면 고정값이기때문에 앞서 말한 방법대로 구할 수 있습니다.
하지만 input과 activation은 고정된 값이 아니기 때문에
input batch를 넣어 input과 activation의 분포를 구한 뒤 같은 방법으로 quantization을 수행합니다
이를 calibration이라고 합니다
참고로 bias의 quantization는
$S_{biases} = S_{weights}*S_{activations}$
$Z_{biases}=0$
입니다
Inference에서 곱셈이 일어나는데 다음과 같은 방법으로 연산이 수행됩니다
(Y = Wx+b)
(matrix @ matrix 라고 가정)
$S_y(y_3^{i,k}-Z_y) = \sum_{j=1}^{N}[S_w(q_w^{i,j}-Z_w)*S_x(q_x^{j,k}-Z_x)]$
$q_y^{i,k} = Z_y + \frac{S_w*S_x}{S_y}\sum_{j=1}^{N}[(q_w^{i,j}-Z_w)*(q_x^{j,k}-Z_x)]$
$q_y^{i,k} = Z_y + \frac{S_w*S_x}{S_y}\sum_{j=1}^{N}[q_w^{i,j}*q_x^{j,k}+Z_w*Z_x-Z_w*q_x^{j,k}-Z_x*q_w^{i,j}]$
$q_x$는 input에 따라 달라지는 값입니다. 나머지 값들은 고정된 값이기 때문에 미리 계산할 수 있습니다.
Quantization Aware Training
quantization을 고려하여 학습합니다
fake quantization을 통해 quantization이 모델에 불러오는 성능을 함께 학습합니다
하지만 여기서 backpropagation에 문제가 있는데,
wt quant와 act quant는 quantization을 위한 round 연산에 의해 미분이 불가능합니다 (아래 그래프 참고)
따라서 모델을 학습하기 위해 backpropagation 단계에서 fake quantization의 기울기를 항상 1이라고 계산합니다
이를 STE(Straight Through Estimator)
QAT를 쓰는것이 왜 더 좋은지를 알아봅시다
quantization으로 인한 noise 때문에 float으로 학습했을때보다 QAT에서는 local minima로 narrow한 지점에 안착하기 쉽지 않습니다
narrow한 지점은 quantization 변환 시 더 큰 변화의 폭을 가집니다.
PTA는 quantization으로인한 변화의 폭이 크므로 더 성능이 좋지 못합니다
https://pytorch.org/blog/quantization-in-practice/
'인공지능 > 최적화' 카테고리의 다른 글
Convolution in Detail (0) | 2024.03.25 |
---|