
01 前言
近期在学习 Qwen3 的模型结构时,看到了 Qwen 使用了 GPTQ 与 AWQ 量化方案,于是便萌生了介绍 LLM 量化技术的想法,笔者将用 2-3 篇文章,给读者们介绍大模型量化的技术。
量化是指将高精度计算的浮点型数据近似为低比特位数据(如 int16、int8、int4 等)的过程,此过程需在不显著损耗精度的同时,提升模型推理效率并降低内存占用。特别是在当前主流大语言模型(LLM)的参数量轻松突破万亿规模的情况下,量化技术对于高效低成本部署 LLM 尤为重要。而且由于 LLM 的参数量巨大,当前主流的模型都采用 PTQ 后量化技术,从而降低量化过程带来的成本。
在正式开始这篇文章之前,我们首先来了解一下 LLM 量化的相关概念。
02 LLM 量化相关概念
2.1 LLM 量化常用的数值格式

2.2 LLM 量化对象
在部署推理时,LLM 的量化对象与传统的 CNN 有所不同,除了权重与激活以外,还增加了 LLM 特有的 KV Cache。所以,LLM 的量化对象主要是权重、激活和 KV Cache。
- **权重量化:**仅对 LLM 中的权重进行量化,常见的方法有 GPTQ (W4A16,权重量化为 INT4,激活保持 FP16/BF16)、AWQ(W4A16/W8A16)等;
- **激活量化:**对 LLM 中的激活进行量化,常见的方法有 SmoothQuant (W8A8)、LLM.int8()等,由于激活分布范围大且动态变化,相比权重量化更具挑战;
- **KV****Cache 量化:**在 LLM 推理中,为避免重复计算,会缓存 Attention 中的 Key/Value 向量(KV Cache)。 KV Cache 的大小与 上下文长度线性相关,是长文本推理时的主要显存瓶颈。常见的方法有 KV Cache INT8/INT4 量化。
LLM 的实际部署过程中,常见的量化方案包括:
- W4A16(GPTQ、AWQ) :权重量化为 INT4,激活保持 FP16/BF16。
- W8A16 : 权重量化为 INT8,激活保持 FP16/BF16。
- W8A8(SmoothQuant): 权重和激活均量化为 INT8。
- KV****Cache INT8 :缓解长上下文显存开销。
下面,我们将对具体的量化方法进行介绍。
03 主流 LLM 量化方法介绍
Qwen 系列模型使用了 AWQ、GPTQ 和 llama.cpp 中的量化技术,且推荐使用 AWQ 结合 AutoAWQ,所以本节我们先介绍此方法。
3.1 AWQ 结合 AutoAWQ 量化方法介绍及使用示例
AWQ 全称为 ACTIVATION-AWARE WEIGHT QUANTIZATION,即**激活感知的权重量化,**是一种针对 LLM 的低比特权重量化的硬件友好方法。AWQ 在业界广泛应用,除了官方的支持 llm-awq 外,AutoAWQ、vLLM、 HuggingFace NVIDIA TensorRT-LLM、FastChat 等主流模型或框架也提供了对 AWQ 的支持。
3.1.1 AWQ量化技术原理
AWQ 作者认为:
- 权重对于大语言模型的性能并不同样重要, 有一小部分(0.1%-1%)对模型精度影响较大的关键权重;跳过这些关键权重的量化将显著减少量化精度损失。
- 而且,关键权重对应于较大激活幅度的权重通道更加显着,因为它们处理更重要的特征,从而根据这个现象寻找关键权重。尽管将 0.1% 的权重保留为 FP16 可以在不明显增加模型大小的情况下提高量化性能,但这种混合精度数据类型会给系统实现带来困难(硬件效率低下)。
- 设计了一种 per-channel 缩放方法来自动搜索最佳缩放,从而减少显著权重的量化误差,这种方法不存在硬件效率低下的问题。

PPL:即困惑度 Perplexity,是语言模型预测序列的平均不确定性度量。PPL 越小,表示模型越“自信”且预测越接近真实分布;PPL 越大,说明预测分布和真实分布偏差更大。
上图是作者的实验,可以看出:
- 左图:所有的权重都从 FP16 量化到 INT3,PPL 为 43.2;
- 中图:基于激活分布找到了 1%的关键权重,将关键权重保持 FP16 精度,其余权重量化到 INT3,PPL 由 43.2 大幅下降至 13.0,但这种混合精度格式在硬件上运行并不高效;
- 右图: AWQ 执行 per-channel 缩放以保护关键权重从而减少量化误差,这里可以看到缩放 weight 后再做量化的 PPL 为 13.0,缩放本身未对精度产生影响。
权重的缩放因子 s 为超参数,作者在OPT-6.7B模型上做了对比实验,发现当 s 比较大比如等于 4 时,非关键通道的相对误差将会增加(非显著通道的误差将被放大)。

为了同时考虑关键权重和非关键权重,AWQ 选择自动搜索最佳(每个输入通道)缩放因子,使某一层量化后的输出差最小。这就把量化问题建模为如下的最优化问题:

为提升该过程的稳定性,我们通过分析影响缩放因子(scaling factor)选择的相关因素,为最优缩放比例(optimal scale)定义了一个搜索空间(search space)。如前一部分所述,权重通道(weight channels)的显著性实际上由激活值缩放比例(activation scale)决定(即 “激活感知性”,activation-awareness)。因此,AWQ 采用了一个极为简洁的搜索空间,具体如下:

其中 α 是用于平衡对关键 channel 与非关键 channel 的保护力度。通过在区间 [0, 1] 内执行快速网格搜索(grid search),可确定最优的 α 值(其中 α=0 代表不进行缩放;α=1 代表在我们的搜索空间内采用最激进的缩放策略)。此外,论文中还引入了权重裁剪(weight clipping)操作,以最小化量化过程中的均方误差(MSE)。
3.1.2 AWQ量化模型示例
AWQ****与 HuggingFace Transformers 无缝兼容,加载模型后可以直接 .quantize()做量化,相关使用流程如下。
安装依赖
pip3 install transformers accelerate autoawq
量化模型
from awq import AutoAWQForCausalLM
from transformers import AutoTokenizer
from transformers import AwqConfig
model_path = "facebook/opt-125m"
quant_path = "opt-125m-awq"
#量化参数配置
quant_config = {
"zero_point": True,
"q_group_size": 128,
"w_bit": 4,
"version": "GEMM"
}
# 加载模型
model = AutoAWQForCausalLM.from_pretrained(model_path, device_map="auto")
tokenizer = AutoTokenizer.from_pretrained(model_path, trust_remote_code=True)
#准备校准数据
data = []
for msg in dataset:
text = tokenizer.apply_chat_template(msg, tokenize=False, add_generation_prompt=False)
data.append(text.strip())
# 量化
model.quantize(tokenizer, quant_config=quant_config,calib_data=data)
# 修改配置,保证和 Transformers 兼容
quantization_config = AwqConfig(
bits=quant_config["w_bit"],
group_size=quant_config["q_group_size"],
zero_point=quant_config["zero_point"],
version=quant_config["version"].lower(),
).to_dict()
model.model.config.quantization_config = quantization_config
# 保存模型
model.save_quantized(quant_path, safetensors=True, shard_size="4GB")
tokenizer.save_pretrained(quant_path)
quant_config 参数解析:
"w_bit": 权重量化的位宽"q_group_size":量化不是对整个权重张量做一次缩放,而是分组处理,上述示例选择每组 128 个权重会共享一组缩放因子(scale)和零点(zero point),128是一个常用折中值(Meta 在 LLaMA-2/3 的 INT4 AWQ 中也常用 128)。"zero_point":是否使用零点(zero point)补偿,如果设成False,就是对称量化(中心对齐 0),如果设成True,就是非对称量化,可以更好覆盖权重分布,提高精度。"version":底层推理内核类型(后端实现方式)。GEMM:通用矩阵乘法(General Matrix Multiplication),适合大模型的权重矩阵乘法。GEMV:矩阵-向量乘法(适合批次小、延迟敏感的场景)。一般推荐用GEMM,因为推理框架(Transformers, vLLM 等)大部分优化都是基于 GEMM 内核。
加载量化后的模型进行推理
from transformers import AutoTokenizer, AutoModelForCausalLM
quant_path = "opt-125m-awq"
tokenizer = AutoTokenizer.from_pretrained(quant_path, trust_remote_code=True)
model = AutoModelForCausalLM.from_pretrained(quant_path, device_map="auto")
text = "Hello my name is"
inputs = tokenizer(text, return_tensors="pt").to(0)
out = model.generate(**inputs, max_new_tokens=20)
print(tokenizer.decode(out[0], skip_special_tokens=True))
3.2GPTQ
GPTQ(Gradient Post-Training Quantization)是一种针对类 GPT 大型语言模型的量化方法,它基于近似二阶信息进行一次性权重量化。本节将会介绍 GPTQ 量化的基本原理,同时也会展示如何通过 AutoGPTQ 来对您自己的模型进行量化处理。GPTQ 量化具有以下特点:
GPTQ 量化的优点:
- 无须重新训练(仅需少量校准数据)。
- 量化精度接近全精度,4bit GPTQ 能维持 LLaMA、OPT 等模型接近 FP16 的性能。
- 速度快,实用性强,已成为主流 LLM 低比特推理方法。
GPTQ 量化的缺点:
- 量化过程涉及 Hessian 矩阵近似和逐元素优化,计算复杂度较高。
- 一般只量化权重,激活量化效果不佳(通常保持 FP16)。
3.2.1 GPTQ 量化技术原理
GPTQ 是一种高精度、高效率的量化方法,它可以在大约四个 GPU 小时内量化具有 1750 亿个参数的 GPT 模型,将位宽降低到每个权重 3 位或 4 位,与未压缩基线相比,精度下降可以忽略不计。GPTQ 源于 OBQ(Optimal Brain Quantization),而 OBQ 改进自剪枝方法 OBS(Optimal Brain Surgeon),OBS 又源自 Yann LeCun 1990 年提出的 OBD(Optimal Brain Damage)。OBD 通过泰勒展开简化目标函数并计算海森矩阵确定参数影响;OBS 考虑参数交叉项,求海森矩阵逆确定剪枝顺序并更新其他参数减少误差。OBQ 将剪枝思路推广到量化,视剪枝为近似 0 的特殊量化,但速度慢,大模型量化需数天。GPTQ 作为 OBQ 加速版,优化算法性能,降低复杂度并保证精度,176B Bloom 模型量化不到 4 小时,且有严谨数学理论推导。
GPTQ 在执行量化操作时,会先对权重实施分组处理(比如,每 128 列划分为一个组),进而构成若干个数据块。对于每个数据块里的全部参数,会逐一开展量化工作。在完成某一个参数的量化后,借助校准数据集,对该数据块中其余还未进行量化的参数进行合理调节,通过这种方式来补偿量化过程中产生的精度损耗。GPTQ 的量化过程如下所示:

先用一小部分校准数据(calibration data,通常只需几百到几千条样本,比如来自模型训练语料的子集),将校准数据喂入原始全精度模型,收集每一层的 激活值(输入向量 X)。
GPTQ 的目标是 最小化量化后输出误差的二次形式:

其中 WX 为量化前的权重和激活输入,另外一项为量化后的权重和激活。
GPTQ 使用输入激活的协方差来近似 Hessian,这样就转化为公式(2)中的问题:

GPTQ 不一次性量化整个权重矩阵,而是 逐元素(或逐块)地量化权重。对每个权重,在量化时会根据 Hessian 的对角线项(近似二阶导信息)进行 误差校正,首先量化一个权重,然后更新剩余权重的“残差误差”,这相当于执行一次 逐步的高斯消元式校正,避免量化误差累积。

重复上述步骤,依次处理完一层的全部权重。然后继续到下一层,直到整个模型量化完成。
3.2.2 GPTQ 量化使用示例
transformers 已经正式支持了 AutoGPTQ,这意味着您能够直接在transformers中使用量化后的模型。
安装依赖
推荐通过安装源代码的方式获取并安装 AutoGPTQ 工具包:
git clone https://github.com/AutoGPTQ/AutoGPTQ
cd AutoGPTQ
pip install -e .
量化模型
import os
import logging
import torch
from auto_gptq import AutoGPTQForCausalLM, BaseQuantizeConfig
from transformers import AutoTokenizer
# =============================
# 配置路径和量化超参数
# =============================
model_path = "your_model_path" # 原始模型路径(本地或HF Hub)
quant_path = "your_quantized_model_path" # 保存量化后模型的路径
# 量化配置
quantize_config = BaseQuantizeConfig(
bits=4, # 量化比特数,可选 4 或 8
group_size=128, # 分组大小,推荐 128
damp_percent=0.01, # Hessian 阻尼因子,提升数值稳定性
desc_act=False, # 是否对激活值量化,一般 False 以提升推理速度
static_groups=False, # 是否使用静态分组,通常 False
sym=True, # 是否对称量化,True 更稳定
true_sequential=True, # 是否顺序量化,提升精度但更慢
model_name_or_path=None, # 保持 None(除非做特殊兼容)
model_file_base_name="model" # 保存的模型文件前缀
)
max_len = 8192 # 输入最大长度(根据模型上下文窗口设置)
# =============================
# 加载分词器和模型
# =============================
tokenizer = AutoTokenizer.from_pretrained(model_path, use_fast=True)
# 确保 pad_token 存在(某些 LLM 没有定义 pad_token)
if tokenizer.pad_token is None:
tokenizer.pad_token = tokenizer.eos_token
model = AutoGPTQForCausalLM.from_pretrained(model_path, quantize_config)
# =============================
# 准备校准数据(calibration data)
# dataset 需要你自己定义,比如一小部分语料
# dataset = ["hello world", "some calibration sentence", ...]
# =============================
data = []
for msg in dataset:
# 转换成文本(可根据是否使用 chat 模板决定)
text = tokenizer.apply_chat_template(
msg,
tokenize=False,
add_generation_prompt=False
)
# 编码输入
model_inputs = tokenizer(
text,
truncation=True,
max_length=max_len,
padding="max_length", # 保证对齐
return_tensors="pt"
)
# 收集数据(dict 格式)
data.append(dict(
input_ids=model_inputs["input_ids"].squeeze(0),
attention_mask=model_inputs["attention_mask"].squeeze(0)
))
# =============================
# 配置日志输出
# =============================
logging.basicConfig(
format="%(asctime)s %(levelname)s [%(name)s] %(message)s",
level=logging.INFO,
datefmt="%Y-%m-%d %H:%M:%S"
)
# =============================
# 执行量化
# =============================
model.quantize(data, cache_examples_on_gpu=False)
# =============================
# 保存量化后的模型和分词器
# =============================
os.makedirs(quant_path, exist_ok=True)
model.save_quantized(quant_path, use_safetensors=True)
tokenizer.save_pretrained(quant_path)
print(f"量化模型已保存到: {quant_path}")
如何学习大模型 AI ?
由于新岗位的生产效率,要优于被取代岗位的生产效率,所以实际上整个社会的生产效率是提升的。
但是具体到个人,只能说是:
“最先掌握AI的人,将会比较晚掌握AI的人有竞争优势”。
这句话,放在计算机、互联网、移动互联网的开局时期,都是一样的道理。
我在一线互联网企业工作十余年里,指导过不少同行后辈。帮助很多人得到了学习和成长。
我意识到有很多经验和知识值得分享给大家,也可以通过我们的能力和经验解答大家在人工智能学习中的很多困惑,所以在工作繁忙的情况下还是坚持各种整理和分享。但苦于知识传播途径有限,很多互联网行业朋友无法获得正确的资料得到学习提升,故此将并将重要的AI大模型资料包括AI大模型入门学习思维导图、精品AI大模型学习书籍手册、视频教程、实战学习等录播视频免费分享出来。

第一阶段(10天):初阶应用
该阶段让大家对大模型 AI有一个最前沿的认识,对大模型 AI 的理解超过 95% 的人,可以在相关讨论时发表高级、不跟风、又接地气的见解,别人只会和 AI 聊天,而你能调教 AI,并能用代码将大模型和业务衔接。
- 大模型 AI 能干什么?
- 大模型是怎样获得「智能」的?
- 用好 AI 的核心心法
- 大模型应用业务架构
- 大模型应用技术架构
- 代码示例:向 GPT-3.5 灌入新知识
- 提示工程的意义和核心思想
- Prompt 典型构成
- 指令调优方法论
- 思维链和思维树
- Prompt 攻击和防范
- …
第二阶段(30天):高阶应用
该阶段我们正式进入大模型 AI 进阶实战学习,学会构造私有知识库,扩展 AI 的能力。快速开发一个完整的基于 agent 对话机器人。掌握功能最强的大模型开发框架,抓住最新的技术进展,适合 Python 和 JavaScript 程序员。
- 为什么要做 RAG
- 搭建一个简单的 ChatPDF
- 检索的基础概念
- 什么是向量表示(Embeddings)
- 向量数据库与向量检索
- 基于向量检索的 RAG
- 搭建 RAG 系统的扩展知识
- 混合检索与 RAG-Fusion 简介
- 向量模型本地部署
- …
第三阶段(30天):模型训练
恭喜你,如果学到这里,你基本可以找到一份大模型 AI相关的工作,自己也能训练 GPT 了!通过微调,训练自己的垂直大模型,能独立训练开源多模态大模型,掌握更多技术方案。
到此为止,大概2个月的时间。你已经成为了一名“AI小子”。那么你还想往下探索吗?
- 为什么要做 RAG
- 什么是模型
- 什么是模型训练
- 求解器 & 损失函数简介
- 小实验2:手写一个简单的神经网络并训练它
- 什么是训练/预训练/微调/轻量化微调
- Transformer结构简介
- 轻量化微调
- 实验数据集的构建
- …
第四阶段(20天):商业闭环
对全球大模型从性能、吞吐量、成本等方面有一定的认知,可以在云端和本地等多种环境下部署大模型,找到适合自己的项目/创业方向,做一名被 AI 武装的产品经理。
- 硬件选型
- 带你了解全球大模型
- 使用国产大模型服务
- 搭建 OpenAI 代理
- 热身:基于阿里云 PAI 部署 Stable Diffusion
- 在本地计算机运行大模型
- 大模型的私有化部署
- 基于 vLLM 部署大模型
- 案例:如何优雅地在阿里云私有部署开源大模型
- 部署一套开源 LLM 项目
- 内容安全
- 互联网信息服务算法备案
- …
学习是一个过程,只要学习就会有挑战。天道酬勤,你越努力,就会成为越优秀的自己。
如果你能在15天内完成所有的任务,那你堪称天才。然而,如果你能完成 60-70% 的内容,你就已经开始具备成为一名大模型 AI 的正确特征了。
这份完整版的大模型 AI 学习资料已经上传优快云,朋友们如果需要可以微信扫描下方优快云官方认证二维码免费领取【保证100%免费】

2万+

被折叠的 条评论
为什么被折叠?



