大模型的开发应用(十八):大模型量化:GPTQ与AWQ

大模型量化:GPTQ与AWQ

0 前言

前面在介绍QLoRA的时候,我们介绍了 NF4 和 LLM.int8() 量化,这两种量化方式是比较常用的大模型在线量化方式,对于离线量化,目前比较常用的是 GPTQ 和 AWQ。当然,我个人做过对比实现,发现 GPTQ 和 AWQ 效果都不好容易导致模型智商下降,但面试的时候又经常被问到,因此在此对这两种量化方式做个详细的介绍。本文涉及到了比较多的数学推导,读者最好知道多元函数的泰勒泰勒展开、运筹优化的标准数学表达式和 L2 范数的含义,其他像拉格朗日乘数、Cholesky 分解。

本文主要参考了知乎博主杨远航的文章QLoRA、GPTQ:模型量化概述

1 GPTQ 的基础

1.1 海森矩阵

定义

海森矩阵(Hessian Matrix)是一个描述多元函数局部曲率性质的二阶偏导数方阵,由德国数学家路德维希·奥托·赫斯(Ludwig Otto Hesse)于19世纪提出,因此得名。它在优化、图像处理、机器学习等领域有广泛应用。以下从数学形式、性质和应用场景展开说明:

对于一个 n 元实值函数 f ( w 1 , w 2 , ... , w n ) f(w_1, w_2, \ldots, w_n) f(w1,w2,...,wn),若其二阶偏导数均存在,其海森矩阵 H ( f ) \mathbf{H}(f) H(f) 是一个 n×n 的对称矩阵,定义为:

H ( f ) = [ ∂ 2 f ∂ w 1 2 ∂ 2 f ∂ w 1 ∂ w 2 ⋯ ∂ 2 f ∂ w 1 ∂ w n ∂ 2 f ∂ w 2 ∂ w 1 ∂ 2 f ∂ w 2 2 ⋯ ∂ 2 f ∂ w 2 ∂ w n ⋮ ⋮ ⋱ ⋮ ∂ 2 f ∂ w n ∂ w 1 ∂ 2 f ∂ w n ∂ w 2 ⋯ ∂ 2 f ∂ w n 2 ] \mathbf{H}(f) = \begin{bmatrix} \frac{\partial^2 f}{\partial w_1^2} & \frac{\partial^2 f}{\partial w_1 \partial w_2} & \cdots & \frac{\partial^2 f}{\partial w_1 \partial w_n} \\ \frac{\partial^2 f}{\partial w_2 \partial w_1} & \frac{\partial^2 f}{\partial w_2^2} & \cdots & \frac{\partial^2 f}{\partial w_2 \partial w_n} \\ \vdots & \vdots & \ddots & \vdots \\ \frac{\partial^2 f}{\partial w_n \partial w_1} & \frac{\partial^2 f}{\partial w_n \partial w_2} & \cdots & \frac{\partial^2 f}{\partial w_n^2} \end{bmatrix} H(f)= ∂w12∂2f∂w2∂w1∂2f⋮∂wn∂w1∂2f∂w1∂w2∂2f∂w22∂2f⋮∂wn∂w2∂2f⋯⋯⋱⋯∂w1∂wn∂2f∂w2∂wn∂2f⋮∂wn2∂2f

关键点

  • 矩阵元素为函数对变量两两组合的二阶偏导数 ∂ 2 f ∂ w i ∂ w j \frac{\partial^2 f}{\partial w_i \partial w_j} ∂wi∂wj∂2f;
  • 若函数二阶连续可导,则矩阵对称 ( ∂ 2 f ∂ w i ∂ w j = ∂ 2 f ∂ w j ∂ w i (\frac{\partial^2 f}{\partial w_i \partial w_j} = \frac{\partial^2 f}{\partial w_j \partial w_i} (∂wi∂wj∂2f=∂wj∂wi∂2f)。

核心性质

  1. 对称性

    当函数二阶偏导数连续时,海森矩阵是对称矩阵,混合偏导数与求导顺序无关。

  2. 与泰勒展开的关系

    函数在点 w 0 \mathbf{w}_0 w0 处的二阶泰勒展开为:

    f ( w ) ≈ f ( w 0 ) + ∇ f ( w 0 ) T ( w − w 0 ) + 1 2 ( w − w 0 ) T H ( f ) ( w 0 ) ( w − w 0 ) f(\mathbf{w}) \approx f(\mathbf{w}_0) + \nabla f(\mathbf{w}_0)^T (\mathbf{w} - \mathbf{w}_0) + \frac{1}{2} (\mathbf{w} - \mathbf{w}_0)^T \mathbf{H}(f)(\mathbf{w}_0) (\mathbf{w} - \mathbf{w}_0) f(w)≈f(w0)+∇f(w0)T(w−w0)+21(w−w0)TH(f)(w0)(w−w0)

    其中 H ( f ) \mathbf{H}(f) H(f) 决定了函数的局部曲率(凸性/凹性)。

  3. 极值判定(了解即可,不重要)

    在梯度 ∇ f = 0 \nabla f = 0 ∇f=0 的临界点 w 0 \mathbf{w}_0 w0 处:

    • 若 H \mathbf{H} H 正定 (所有特征值 > 0)→ 局部极小值
    • 若 H \mathbf{H} H 负定 (所有特征值 < 0)→ 局部极大值
    • 若 H \mathbf{H} H 不定 (特征值有正有负)→ 鞍点(非极值)。

1.2 OBD(Optimal Brain Damage)算法原理

这是发表于1990年的关于神经网络的剪枝算法,关于模型剪枝,实际上就是去掉神经网络中的一些不重要的连接,表现在权重矩阵上,就是把矩阵中的一些元素改成0。剪枝最大的挑战在于,你不知道哪些连接该剪,哪些不该剪。这需要有一套规则来进行判断,不同的剪枝算法,对应的判断规则不一样。

OBD算法则是通过泰勒展开近似替代原始模型,进而计算各个参数对目标函数(损失函数)的影响,以此来判断剪枝的优先级。

先假设模型的输入数据是固定的,E 表示损失函数,那么 E = f ( w 1 , w 2 , ... , w n ) E=f(w_1, w_2, \ldots, w_n) E=f(w1,w2,...,wn), Δ E \Delta E ΔE 表示参数变化( Δ w \Delta \mathbf w Δw)给损失函数带来影响,则有:

Δ E = f ( w 1 + Δ w 1 , w 2 + Δ w 2 , ... , w n + Δ w n ) − f ( w 1 , w 2 , ... , w n ) = f ( w 1 , w 2 , ... , w n ) + ∑ i g i Δ w i + 1 2 ∑ i h i i Δ w i 2 + 1 2 ∑ i ≠ j h i j Δ w i Δ w j + O ( Δ w 3 ) − f ( w 1 , w 2 , ... , w n ) = ∑ i g i Δ w i + 1 2 ∑ i h i i Δ w i 2 + 1 2 ∑ i ≠ j h i j Δ w i Δ w j + O ( Δ w 3 ) \begin{align*} \Delta E &= f(w_1+\Delta w_1, w_2+\Delta w_2, \ldots, w_n+\Delta w_n) - f(w_1, w_2, \ldots, w_n) \\ &= f(w_1, w_2, \ldots, w_n) + \sum_{i} g_{i} \Delta w_{i} + \frac{1}{2} \sum_{i} h_{ii} \Delta w_{i}^{2} + \frac{1}{2} \sum_{i \neq j} h_{ij} \Delta w_{i} \Delta w_{j} + O\left( \Delta \mathbf{w}^{3} \right) - f(w_1, w_2, \ldots, w_n) \\ &= \sum_{i} g_{i} \Delta w_{i} + \frac{1}{2} \sum_{i} h_{ii} \Delta w_{i}^{2} + \frac{1}{2} \sum_{i \neq j} h_{ij} \Delta w_{i} \Delta w_{j} + O\left( \Delta \mathbf{w}^{3} \right) \end{align*} ΔE=f(w1+Δw1,w2+Δw2,...,wn+Δwn)−f(w1,w2,...,wn)=f(w1,w2,...,wn)+i∑giΔwi+21i∑hiiΔwi2+21i=j∑hijΔwiΔwj+O(Δw3)−f(w1,w2,...,wn)=i∑giΔwi+21i∑hiiΔwi2+21i=j∑hijΔwiΔwj+O(Δw3)

式中加黑部分表示向量,此外:

  • g i = ∂ E ∂ w i g_{i} = \dfrac{\partial E}{\partial w_{i}} gi=∂wi∂E 为参数的一阶偏导
  • h i j = ∂ 2 E ∂ w i ∂ w j h_{ij} = \dfrac{\partial^{2} E}{\partial w_{i} \partial w_{j}} hij=∂wi∂wj∂2E 为海森矩阵的元素
  • h i i h_{ii} hii 为对角线元素

OBD 简化假设

  • 假设目标函数是二阶的,因此忽略高阶项 O ( Δ w 3 ) O(\Delta \mathbf w^{3}) O(Δw3)
  • 模型训练充分收敛,所有参数一阶偏导为零: g i = 0 , ∀ i g_{i} = 0,\quad \forall i gi=0,∀i
  • 假设删除任意一个参数后,其他参数对目标函数的影响不变。也就是说,每个参数对目标函数的影响是独立的。于是我们也可以不考虑交叉项:: h i j = 0 , ∀ i , j , i ≠ j h_{ij} = 0,\quad \forall i,j,\ i \neq j hij=0,∀i,j, i=j

基于上述假设,公式可简化为:
Δ E = 1 2 ∑ i h i i Δ w i 2 \Delta E = \frac{1}{2} \sum_{i} h_{ii} \Delta w_{i}^{2} ΔE=21i∑hiiΔwi2

若将神经网络中参数 w i w_i wi 对应的连接删除,即令 Δ w i = − w i \Delta w_i = -w_i Δwi=−wi,其他参数不变,则对目标函数的影响为: Δ E = 1 2 h i i w i 2 \Delta E = \frac{1}{2} h_{ii} w_{i}^{2} ΔE=21hiiwi2

剪枝次序确定

通过计算参数对应的海森矩阵对角元素: h i i = ∂ 2 E ∂ w i 2 h_{ii} = \dfrac{\partial^{2} E}{\partial w_{i}^{2}} hii=∂wi2∂2E,可以按照下面的方式确定剪枝的优先级:

  1. 按 h i i w i 2 h_{ii} w_{i}^{2} hiiwi2 值升序排序
  2. 优先删除影响最小的参数。

1.3 OBS(Optimal Brain Surgeon)算法原理

(1)基本原理与首次剪枝

OBS 认为,参数之间的独立性不成立,因为真实模型无法用数学表达式表达出来,上面的泰勒展开式只是近似,我们还是要考虑交叉项,因此有:
Δ E = 1 2 ∑ i h i i Δ w i 2 + 1 2 ∑ i ≠ j h i j Δ w i Δ w j = 1 2 Δ w T H Δ w \Delta E = \frac{1}{2} \sum_{i} h_{ii} \Delta w_{i}^{2}+\frac{1}{2} \sum_{i \neq j} h_{ij} \Delta w_{i} \Delta w_{j} = \frac{1}{2} \Delta \mathbf{w}^{\mathrm{T}} \mathbf{H} \Delta \mathbf{w} ΔE=21i∑hiiΔwi2+21i=j∑hijΔwiΔwj=21ΔwTHΔw

式中加黑部分表示向量或者矩阵。

现在我们假设删除一个权重后,可以调整其他权重参数,来抵消剪枝带来的影响。

若删除权重 w q w_q wq,即 Δ w \Delta \mathbf{w} Δw 的第 q q q 维固定为 − w q -w_q −wq,但其他维度的值可变,用以抵消剪枝带来的影响,那么此时可以得到一个约束条件:
e q T ⋅ Δ w + w q = 0 \mathbf{e}{\mathbf{q}}^{\mathbf{T}} \cdot \Delta \mathbf{w} + w{q} = 0 eqT⋅Δw+wq=0

其中, e q \mathbf{e}_{\mathbf{q}} eq 为 one-hot 向量,第 q q q 个分量为 1,其他分量为 0。

接下来要寻找最优的权重索引 q q q,使得将 w \mathbf{w} w 的第 q q q 个维度置零后,通过调整其他权重 Δ w i \Delta w_i Δwi( i ≠ q i \neq q i=q),使剪枝给损失函数 E E E 带来的影响最小。当然,这个听起来有点绕,说得浅显一点就是,先预判每个权重删除+系统补偿后的最小损失变化,然后选择影响最小的权重(假设索引为 q) 优先剪枝,以此模型压缩中的性能-精简度最优平衡。

寻找 q q q 的过程,可以表示为一个最优化问题:

min ⁡ Δ w , q 1 2 Δ w T H Δ w subject to e q T ⋅ Δ w + w q = 0 \min {\Delta \mathbf{w}, q} \frac{1}{2} \Delta \mathbf{w}^{\mathrm{T}} \mathbf{H} \Delta \mathbf{w} \\ \quad \text{subject to} \quad \mathbf{e}{q}^{\mathrm{T}} \cdot \Delta \mathbf{w} + w_{q} = 0 Δw,qmin21ΔwTHΔwsubject toeqT⋅Δw+wq=0

学过运筹学的同学对上面的表达式会比较熟悉,这是一个凸优化问题,可以通过 Lagrange 乘数法求解。

定义函数:
L = 1 2 Δ w T H Δ w + λ ( e q T ⋅ Δ w + w q ) L = \frac{1}{2} \Delta \mathbf{w}^{\mathrm{T}} \mathbf{H} \Delta \mathbf{w} + \lambda \left( \mathbf{e}{q}^{\mathrm{T}} \cdot \Delta \mathbf{w} + w{q} \right) L=21ΔwTHΔw+λ(eqT⋅Δw+wq)

优化结果为:
Δ w = − w q [ H − 1 ] q q H − 1 ⋅ e q and L = 1 2 w q 2 [ H − 1 ] q q \Delta \mathbf{w} = -\frac{w_{q}}{ \left[ \mathbf{H}^{-1} \right]{qq} } \mathbf{H}^{-1} \cdot \mathbf{e}{q} \quad \text{and} \quad L = \frac{1}{2} \frac{w_{q}^{2}}{ \left[ \mathbf{H}^{-1} \right]_{qq} } Δw=−[H−1]qqwqH−1⋅eqandL=21[H−1]qqwq2

上式中, H − 1 \mathbf{H}^{-1} H−1 表示海森矩阵的逆矩阵, [ H − 1 ] q q [\mathbf{H}^{-1} ]_{qq} [H−1]qq 表示逆矩阵的第 q q q 行第 q q q 列。这部分涉及运筹学知识,不需要掌握,只需要知道优化结果的表达式即可。

从最后的优化结果来看,我们只需要求解海森矩阵的逆,就可以计算每个参数对目标的影响 L q = 1 2 w q 2 [ H − 1 ] q q L_q = \frac{1}{2} \frac{w_{q}^{2}}{ \left[ \mathbf{H}^{-1} \right]_{qq} } Lq=21[H−1]qqwq2。

剪枝的时候,可以先按照影响从小到大给参数排序,然后删除影响最小的权重 w q w_q wq,最后更新其他参数以补偿剪枝带来的影响(只有补偿后,影响才能降到 1 2 w q 2 [ H − 1 ] q q \frac{1}{2} \frac{w_{q}^{2}}{ \left[ \mathbf{H}^{-1} \right]{qq} } 21[H−1]qqwq2),其他参数更新的公式为: w new = w + Δ w \mathbf{w}{\text{new}} = \mathbf{w} + \Delta \mathbf{w} wnew=w+Δw。

(2)迭代剪枝

删除完第一个参数后,如果想继续剪枝,需要更新 H − 1 \mathbf{H}^{-1} H−1,更新的公式如下:
H new − 1 = H − 1 − H − 1 e q e q ⊤ H − 1 [ H − 1 ] q q \mathbf{H}_{\text{new}}^{-1} = \mathbf{H}^{-1} - \frac{\mathbf{H}^{-1} \mathbf{e}_q \mathbf{e}q^{\top} \mathbf{H}^{-1}}{\left[\mathbf{H}^{-1}\right]{qq}} Hnew−1=H−1−[H−1]qqH−1eqeq⊤H−1

随后使用更新后的 H − 1 \mathbf{H}^{-1} H−1 进行下一轮剪枝。

在OBS的算法流程中,过程可以总结为以下几步:

  1. 初始化:训练收敛后,计算全局 H − 1 \mathbf{H}^{-1} H−1(仅需一次)。
  2. 迭代剪枝:
    • 计算每个权重的显著性(saliency) L q = 1 2 w q 2 [ H − 1 ] q q L_q = \frac{1}{2} \frac{w_{q}^{2}}{ \left[ \mathbf{H}^{-1} \right]_{qq} } Lq=21[H−1]qqwq2。
    • 删除显著性最小的权重 w q w_q wq,即在参数向量 w \mathbf{w} w 中,把第 q 维置0。
    • 增量更新 H − 1 \mathbf{H}^{-1} H−1 和剩余权重(使用公式 w new = w + Δ w \mathbf{w}_{\text{new}} = \mathbf{w} + \Delta \mathbf{w} wnew=w+Δw)。
  3. 重复:直接使用更新后的 H − 1 \mathbf{H}^{-1} H−1 进行下一轮剪枝,无需重算。

(3)何时更新 H \mathbf{H} H 和 H − 1 \mathbf{H}^{-1} H−1

上面在迭代剪枝的时候,没有重复计算海森矩阵及其逆矩阵,那什么时候需要重新计算呢?在以下两种情况下可能需要完全重算:

  • 跨层剪枝:当剪枝涉及不同层时,参数间的相关性可能因层结构变化而改变,此时需为每层独立计算 H \mathbf{H} H 和 H − 1 \mathbf{H}^{-1} H−1(如L-OBS方法)
  • 数值稳定性问题:增量更新可能因舍入误差累积导致数值不稳定,此时可定期(如每剪枝100个权重)重新计算 H \mathbf{H} H 和 H − 1 \mathbf{H}^{-1} H−1,以重置误差。

(4)剪枝效果对比:OBS VS OBD

在LeNet5上的剪枝实验表明:

  • 使用优化补偿法(OBS):精度损失仅 0.8%
  • 使用简单指定法(OBD):精度损失达 2.3%
  • 差异来源:关联参数未能主动补偿

1.4 OBC(Optimal Brain Compression)算法原理

OBD 和 OBS 都存在一个缺点,就是剪枝需要计算全参数的海森矩阵(及其它的逆矩阵)。但在动辄上亿参数的神经网络下求解海森矩阵显然不可能。于是,我们可以假设参数矩阵的同一行参数互相之间是相关的,而不同行之间的参数互不相关,这样就只需要在每一行内单独计算海森矩阵就行了。

假如模型的参数是一个 3×3 的矩阵,每一行都有3个参数。在 OBD 或 OBS 中是统一计算模型的全部参数的海森矩阵,这将是一个 9×9 的矩阵,而在 OBC 中,则是对其的每一行计算海森矩阵,那么每个海森矩阵都是一个 3×3 的矩阵,这样的矩阵有3个,示意图如下:

参数矩阵定义与目标函数

假设参数矩阵的维度为 ( d row d_{\text{row}} drow, d col d_{\text{col}} dcol),OBC 论文中,将目标函数定义为:

E = ∑ i = 1 d row ∥ W i , : X − W ^ i , : X ∥ 2 2 E = \sum_{i = 1}^{d_{\text{row}}} \| \mathbf{W}{i,:} \mathbf{X} - \hat{\mathbf{W}}{i,:} \mathbf{X} \|_{2}^{2} E=i=1∑drow∥Wi,:X−W^i,:X∥22

  • W i , : \mathbf{W}_{i,:} Wi,::原始参数矩阵的第 i i i 行向量
  • W ^ i , : \hat{\mathbf{W}}_{i,:} W^i,::压缩(剪枝或量化)后的参数矩阵第 i i i 行向量,如果第 q q q 个参数被剪枝,则对应位置置为0
  • X \mathbf{X} X:输入特征矩阵(隐含定义)
  • ∥ ⋅ ∥ 2 \| \cdot \|_2 ∥⋅∥2: L 2 L_2 L2 范数(欧几里得范数)

注意,这里 E 不再是损失函数了。

直观来看,E 反映的是,参数压缩前后,在同样的输入(具有代表性的校准数据)下,输出结果的差异。

由于每一行的参数相互独立,我们只需为每行量化后的参数 W ^ i , : \hat{\mathbf{W}}_{i,:} W^i,: 计算对应的海森矩阵:

∂ E ∂ W ^ i , : 2 = H i = 2 X X T , ∀ i = 1 , 2 , ⋯   , d row \frac{\partial E}{\partial \hat{\mathbf{W}}{i,:}^{2}} = \mathbf{H}{i} = 2\mathbf{X}\mathbf{X}^{\mathrm{T}}, \quad \forall i = 1, 2, \cdots, d_{\text{row}} ∂W^i,:2∂E=Hi=2XXT,∀i=1,2,⋯,drow

参数矩阵一行共 d col d_{\text{col}} dcol 个参数,如果删除 k 个参数,那么 OBC 的算法流程如下,截图中,M是参数的索引(从1开始):

从 for 循环开始逐行分析:

  • Line 1:找到对目标函数影响最小的参数所在索引 p;
  • Line 2:对第 p 个参数剪枝,并更新其他参数;
  • Line 3:更新 H − 1 \mathbf{H}^{-1} H−1,这里用了数学的等价表达,其实和我们前面介绍的 OBS 更新 H − 1 \mathbf{H}^{-1} H−1 的方式没差,这里 H : , p − 1 H p , : − 1 \mathbf{H}^{-1}{:,p} \mathbf{H}^{-1}{p,:} H:,p−1Hp,:−1 表示第 p 列乘第 p 行。

OBC 还对性能做了一些优化(空间换计算、计算换空间),不过这些和本文主题无关。

总的来说,OBC 就是对每一行使用 OBS 算法,就这么简单。

1.5 OBQ(Optimal Brain Quantization)的算法原理

OBQ 和 OBC 是同一篇文章提出来的,OBQ 认为,剪枝是一种特殊的量化(即剪枝的参数等价于量化到 0 点),即:
lim ⁡ quant ⁡ ( w q ) → 0 量化解 = 剪枝解 \lim_{\operatorname{quant}(w_q) \to 0} \text{量化解} = \text{剪枝解} quant(wq)→0lim量化解=剪枝解

式中, quant ⁡ ( w q ) \operatorname{quant}(w_q) quant(wq) 是参数 w \mathbf{w} w 的第 q q q 维经过量化后的值,当然,这里说的量化,指的是 "量化+反量化"。

我们只需要修改一下 OBC 的约束条件,即可把 OBC 推广到一般量化场景。

一般量化的约束条件按如下方式修改:
e q T ⋅ Δ w + w q = quant ⁡ ( w q ) \mathbf{e}{q}^{\mathrm{T}} \cdot \Delta \mathbf{w} + w{q} = \operatorname{quant}(w_{q}) eqT⋅Δw+wq=quant(wq)

量化后,参数 w \mathbf{w} w 的第 q q q 维的变化量为 quant ⁡ ( w q ) − w q \operatorname{quant}(w_q) - w_q quant(wq)−wq,即 Δ w q = quant ⁡ ( w q ) − w q \Delta w_q= \operatorname{quant}(w_q) - w_q Δwq=quant(wq)−wq

接下来要计算其他参数 Δ w i \Delta w_i Δwi( i ≠ q i \neq q i=q )的更新量,以及 Δ w q \Delta w_q Δwq 量化后的影响(其他参数更新后的补偿影响)。

在OBC中, Δ w q = − w q \Delta w_q= -w_q Δwq=−wq,而这里为 Δ w q = quant ⁡ ( w q ) − w q \Delta w_q= \operatorname{quant}(w_q) - w_q Δwq=quant(wq)−wq,因此只需要将OBC剪枝解中的 w q w_q wq 替换为 w q − quant ⁡ ( w q ) w_q - \operatorname{quant}(w_q) wq−quant(wq),可以得到通用解:
Δ w = − w q − quant ⁡ ( w q ) [ H − 1 ] q q H − 1 ⋅ e q L = 1 2 ( w q − quant ⁡ ( w q ) ) 2 [ H − 1 ] q q \Delta \mathbf{w} = -\frac{w_{q} - \operatorname{quant}(w_{q})}{\left[\mathbf{H}^{-1}\right]{qq}} \mathbf{H}^{-1} \cdot \mathbf{e}{q} \\ L = \frac{1}{2} \frac{\left( w_{q} - \operatorname{quant}(w_{q}) \right)^{2}}{\left[\mathbf{H}^{-1}\right]_{qq}} Δw=−[H−1]qqwq−quant(wq)H−1⋅eqL=21[H−1]qq(wq−quant(wq))2

此公式组实现了OBC框架从剪枝到量化的完美扩展,通过量化误差替代剪枝量保持数学一致性。该结果是OBQ算法(OBC的量化版本)的理论基础,已在GPTQ等现代量化技术中广泛应用。

如果要量化 k 个参数,那么 OBQ 的算法流程如下:

OBQ算法对 k 个参数做量化的时间复杂度为 O ( k ⋅ d c o l 2 ) O(k\cdot d^2_{col}) O(k⋅dcol2),这里 O ( d c o l 2 ) O(d^2_{col}) O(dcol2) 是排序的开销(我个人认为不需要排序,只需要选最小就行了,选最小的时间复杂度是 O ( n ) O(n) O(n),但为何要有平方,这个我就不清楚了)。

量化一般都是整行一起做(下一段会介绍细节),即 k = d c o l k=d_{col} k=dcol,所以对一行做量化的时间复杂度为 O ( d c o l 3 ) O(d^3_{col}) O(dcol3),对整个参数矩阵做量化的时间复杂度为 O ( d r o w ⋅ d c o l 3 ) O(d_{row} \cdot d^3_{col}) O(drow⋅dcol3) 。

若整行一起量化,第 1 个参数量化时,会更新第 2、3、...... 、 d c o l d_{col} dcol 个参数,以补偿量化第 1 个元素带来的影响,但第 2 个参数量化时,只会更新第 3、4、...... 、 d c o l d_{col} dcol 个参数,不会更新第 1 个参数,也就是说,只会更新后面的,不影响前面已量化的。这个和剪枝的时候,计算其他参数的更新值,只计算未剪枝的,不计算已剪得,道理类似。

至此,GPTQ 的前置知识介绍完毕。

2 GPTQ(Gradient-based Post-training Quantization) 算法

GPTQ 是一种针对大型语言模型(LLMs)的高效训练后量化​(PTQ)算法,其核心目标是在不重新训练模型的前提下,将模型权重压缩至低比特(如4-bit),同时最小化精度损失。其原理基于分层误差补偿和海森矩阵优化,结合计算效率改进,实现大规模模型的高效量化。

2.1 原理

OBQ 的算法复杂度还是太高了,GPTQ 对 OBQ 做了一些算法和性能上的优化,以实现大模型的高效量化。

GPTQ 的创新点有:

  • 1 OBS 采用贪心策略,先量化对目标影响最小的参数,但 GPTQ 发现直接按顺序做参数量化,对精度影响也不大。
    • 这项改进使得参数矩阵每一行的量化可以做并行的矩阵计算,同时将时间复杂度从 O ( d r o w ⋅ d c o l 3 ) O(d_{row} \cdot d^3_{col}) O(drow⋅dcol3) 降低到 O ( d c o l 3 ) O(d^3_{col}) O(dcol3),在大模型环境下,这项改进使得量化速度快了一个数量级;
  • 2 Lazy Batch-Updates (惰性批量更新),延迟一部分参数的更新,它能够缓解 bandwidth (带宽)的压力;
  • 3 Cholesky Reformulation,用 Cholesky 分解(柯列斯基分解法)求海森矩阵的逆,在增强数值稳定性的同时,不再需要对海森矩阵做更新计算,进一步减少了计算量。

上述改进中,第一点比较好理解,第三点需要有数值计算方法的基础(理论上说应该是线性代数的知识,但国内本科线性代数普遍不学这个,我是在硕士期间的《数值计算》方法那门课上学的),我们只需要知道第三点用了更稳定的方法计算海森矩阵的逆,了解到这一点就行了。

这里我们重点谈一下第2点:

OBQ 算法在量化某一行时,每次量化一个参数,但本行的其他所有未量化的参数都要更新,以补偿量化带来的影响,也就是说,量化第一个参数要读写参数矩阵 d c o l − 1 d_{col}-1 dcol−1 次,量化第二个参数,要读写参数矩阵 d c o l − 2 d_{col}-2 dcol−2 次,以此类推,整行量化完,读写参数矩阵的时间复杂度为 O ( d c o l 2 ) O(d^2_{col}) O(dcol2) 。

OBQ更新时,若多行并行量化,则参数量化是一列一列按次序进行的,第 i 列的参数的量化结果受到前 i-1 列量化的影响,但第 i 列的量化结果不影响前面列的量化,示意图如下:

对于第 i 列之前的参数(i 从1到 i-1),我们不需要每量化一次就更新一遍第 i 列的参数(这样第 i 列还没量化时,就更新了 i-1 次了),而是可以先记录第 i 列的更新量,等到量化到第 i 列时,再一次性更新参数,这样就可以减少 IO 的次数。

实际操作时,为了减少读写参数矩阵的次数,可以将参数矩阵按每 128 列划分为一个个 group,量化某一列时,同一个 group 内的后面的参数立即更新,后面的 group 只记录更新量。当一个 group 的参数全部量化完成,再统一对后面的所有参数做一次更新,这就是 Lazy Batch-Updates。

Lazy Batch-Updates 示意图如下:

2.2 量化的缩放因子与零点

3 AWQ (Activation-aware Weight Quantization)

是一种先进的低比特权重量化技术,由 MIT 韩松团队于 2023 年提出。其核心目标是通过减少模型显存占用和加速推理,同时最小化精度损失。

3.1 算法原理

研究发现,大模型中仅有 ​0.1%-1% 的权重(显著权重,Salient Weights)​​ 对模型输出影响较大。若保留这些权重的原始精度(FP16),量化其他权重可显著降低量化误差。

显著权重的识别​:通过激活值分布(而非权重自身分布)确定重要权重。激活值较大的通道对应更关键的权重,因其处理更重要的特征

大模型量化中的 AWQ(Activation-aware Weight Quantization) 是一种先进的低比特权重量化技术,由 MIT 韩松团队于 2023 年提出。其核心目标是通过减少模型显存占用和加速推理,同时最小化精度损失。以下是 AWQ 算法原理的详细解析:


一、核心思想:权重重要性差异与激活感知

  1. 权重并非同等重要

    • 研究发现,大模型中仅有 0.1%-1% 的权重(显著权重,Salient Weights) 对模型输出影响较大。若保留这些权重的原始精度(FP16),量化其他权重可显著降低量化误差[citation:1][citation:3][citation:5]。
    • 显著权重的识别:通过激活值分布(而非权重自身分布)确定重要权重。激活值较大的通道对应更关键的权重,因其处理更重要的特征[citation:1][citation:5]。
  2. 缩放保护代替混合精度

    • 直接保留部分权重为 FP16 会导致硬件效率低下(混合精度计算开销大)。
    • AWQ 的解决方案:对显著权重乘以缩放因子(s > 1) ,再量化所有权重。缩放后显著权重的相对量化误差减小,而非显著权重的误差增加较少,整体误差最小化[citation:1][citation:3][citation:5]。
      • 数学原理
        • 量化公式: w ′ = Round ( w ⋅ s / Δ ′ ) w' = \text{Round}(w \cdot s / \Delta') w′=Round(w⋅s/Δ′)
        • 反量化公式: Δ ′ ⋅ w ′ / s \Delta' \cdot w' / s Δ′⋅w′/s
        • 缩放后显著权重的误差比例降为原始误差的 1 / s 1/s 1/s[citation:3][citation:5]。

二、技术实现:自动缩放系数搜索

  1. 目标函数优化

    AWQ 最小化量化后的输出误差:
    min ⁡ s ∥ W X − Q ( W ⋅ s ) ⋅ ( X / s ) ∥ F \min_s \left\| WX - Q(W \cdot s) \cdot (X / s) \right\|_F smin∥WX−Q(W⋅s)⋅(X/s)∥F

    其中 Q Q Q 为量化函数, X X X 为校准数据集的激活值[citation:3][citation:5]。

  2. 简化搜索空间

    • 缩放因子 s s s 与激活幅度相关: s = ( max ⁡ ( ∣ A ∣ ) ) α s = \left( \max(|A|) \right)^\alpha s=(max(∣A∣))α, A A A 为激活值, α \alpha α 为平衡参数。
    • 通过网格搜索(Grid Search)在 [ 0 , 1 ] [0, 1] [0,1] 区间优化 α \alpha α,平衡显著与非显著通道的保护[citation:1][citation:5]。
  3. 硬件友好设计

    • 分组量化:权重按输出通道分组(如每组 128 个权重),每组共享量化参数[citation:1][citation:5]。
    • 权重量化+激活反量化:权重以 INT4 存储,推理时实时解量为 FP16 计算,避免混合精度瓶颈[citation:1][citation:5]。

三、与其他量化方法的对比

特性 AWQ GPTQ
量化原理 激活感知缩放保护显著权重 基于二阶信息的权重重构
精度 更高(接近 FP16) 中等
推理速度 更快(比 GPTQ 快 1.45 倍) 较快
硬件兼容性 无需权重重排序,内核融合优化 需重排序,计算开销大
多模态支持 是(首个成功量化视觉语言模型的方法)
校准数据需求 极少(约 128 样本) 大量

💡 优势总结:AWQ 通过激活感知和自动缩放,在精度、速度和泛化性(支持多模态)上优于 GPTQ 等方案[citation:1][citation:3][citation:5]。


四、实践效果与适用场景

  1. 性能表现

    • 显存压缩:4 比特量化使模型大小减少至 1/4(如 70B 模型从 140GB → 35GB)[citation:1][citation:5]。
    • 速度提升:通过 TinyChat 框架优化(如内核融合、实时解量),推理速度比 FP16 快 3 倍[citation:1][citation:5]。
    • 精度保持:在 LLaMA、Vicuna 等模型上,困惑度(PPL)损失小于 1%[citation:1][citation:5]。
  2. 典型场景

    • 边缘设备:低显存需求(如 4 比特 Qwen-7B 仅需 4GB 显存)[citation:1]。
    • 多模态模型:成功量化 LLaVA 等视觉语言模型[citation:5]。
    • 小 batch 推理:减少增量推理延迟[citation:1]。

关键参数w_bit(量化位数)、q_group_size(分组大小)、version(GEMM 内核优化)。


六、局限性及改进方向

  • 局限性
    • 大 batch 场景可能受限于反量化计算(Compute-bound)[citation:5]。
    • 敏感层(如注意力头)需更高比特数(如 8 位)[citation:3]。
  • 改进方案
    • 层级自适应量化:对不同敏感度的层分配不同比特数[citation:3]。
    • 与硬件协同优化:如 NVIDIA TensorRT-LLM 集成 AWQ 内核[citation:5]。

AWQ 通过 "激活感知缩放"硬件友好设计,在精度与效率间实现了最优平衡,已成为大模型部署的主流量化方案之一。其开源生态(如 AutoAWQ、vLLM)进一步推动了工业落地[citation:1][citation:5]。

这里的思想一直沿用到了 GPTQ 算法:也就是对某个 block 内的所有参数逐个量化,每个参数量化后,需要适当调整这个 block 内其他未量化的参数,以弥补量化造成的精度损失。

相关推荐
weixin_437497773 小时前
读书笔记:Context Engineering 2.0 (上)
人工智能·nlp
喝拿铁写前端3 小时前
前端开发者使用 AI 的能力层级——从表面使用到工程化能力的真正分水岭
前端·人工智能·程序员
goodfat3 小时前
Win11如何关闭自动更新 Win11暂停系统更新的设置方法【教程】
人工智能·禁止windows更新·win11优化工具
北京领雁科技3 小时前
领雁科技反洗钱案例白皮书暨人工智能在反洗钱系统中的深度应用
人工智能·科技·安全
落叶,听雪3 小时前
河南建站系统哪个好
大数据·人工智能·python
清月电子3 小时前
杰理AC109N系列AC1082 AC1074 AC1090 芯片停产替代及资料说明
人工智能·单片机·嵌入式硬件·物联网
Dev7z3 小时前
非线性MPC在自动驾驶路径跟踪与避障控制中的应用及Matlab实现
人工智能·matlab·自动驾驶
七月shi人4 小时前
AI浪潮下,前端路在何方
前端·人工智能·ai编程
橙汁味的风4 小时前
1隐马尔科夫模型HMM与条件随机场CRF
人工智能·深度学习·机器学习
itwangyang5204 小时前
AIDD-人工智能药物设计-AI 制药编码之战:预测癌症反应,选对方法是关键
人工智能