参数量化视觉指南

文摘   2024-08-15 08:30   上海  

正如其名称所示,大型语言模型(LLM)通常太大,无法在消费级硬件上运行。这些模型可能超过数十亿个参数,通常需要具有大量VRAM的GPU来加速推理。

因此,越来越多的研究集中在通过改进训练、适配器等方式使这些模型变小。这一领域的一项主要技术被称为_量化_。

在这篇文章中,我将在语言建模的背景下介绍量化领域,并逐一探讨概念,以发展对该领域的直观理解。我们将探索各种方法、用例以及量化背后的原理。

作为一个视觉指南,期待许多可视化来发展对量化的直观理解!

目录
  • 第一部分:大型语言模型的"问题"

    • 如何表示数值[1]

    • 内存限制[2]

  • 第二部分:量化简介

    • 常见数据类型[3]

      • FP16[4]

      • BF16[5]

      • INT8[6]

    • 对称量化[7]

    • 非对称量化[8]

    • 范围映射和裁剪[9]

    • 校准[10]

    • 权重(和偏置)[11]

    • 激活[12]

  • 第三部分:训练后量化(PTQ)

    • 动态量化[13]

    • 静态量化[14]

    • 4位量化的领域[15]

      • GPTQ[16]

      • GGUF[17]

  • 第四部分:量化感知训练(QAT)

    • 1位大语言模型时代:BitNet[18]

    • 权重量化[19]

    • 激活量化[20]

    • 反量化[21]

    • 所有大型语言模型都在1.58位[22]

    • 0的力量[23]

    • 量化[24]


第1部分:大型语言模型的"问题"

大型语言模型(LLM)因其包含的参数数量而得名。如今,这些模型通常包含数十亿个参数(主要是_权重_),存储起来可能相当昂贵。

在推理过程中,激活值是输入和权重的乘积,同样可能非常大。

因此,我们希望尽可能高效地表示数十亿个值,最大限度地减少存储给定值所需的空间。

让我们从头开始,先探讨数值是如何表示的,然后再对其进行优化。

如何表示数值

给定的值通常表示为浮点数(或计算机科学中的_浮点数_):带小数点的正数或负数。

这些值由""或二进制数字表示。IEEE-754[25] 标准描述了如何使用位来表示值的三个函数之一:符号指数_或_小数(或尾数)

这三个方面可以一起用于根据特定的位值集计算值:

我们用来表示一个值的位数越多,它通常就越精确:

内存限制

我们可用的位数越多,可以表示的值的范围就越大。

给定表示可以采用的可表示数字的区间称为_动态范围_,而两个相邻值之间的距离称为_精度_。

这些位的一个巧妙特性是,我们可以计算出设备存储给定值所需的内存量。由于1字节内存中有8位,我们可以为大多数形式的浮点表示创建一个基本公式。

注意:实际上,在推理过程中还有更多与(V)RAM 数量相关的因素,如上下文大小和架构。

现在假设我们有一个包含700亿个参数的模型。大多数模型原生表示为32位浮点数(通常称为_全精度_),这将需要280GB的内存才能加载模型。

因此,最小化表示模型参数的位数(以及在训练期间!)是非常有吸引力的。然而,随着精度的降低,模型的准确性通常也会降低。

我们希望减少表示值的位数,同时保持准确性...这就是_量化_的用武之地!

第2部分:量化简介

量化旨在将模型参数的精度从较高的位宽(如32位浮点数)降低到较低的位宽(如8位整数)。

在减少表示原始参数的位数时,通常会损失一些精度(粒度)。

为了说明这种效果,我们可以取任何图像并仅使用8种颜色来表示它:

请注意放大的部分看起来比原始图像更"粗糙",因为我们可以使用更少的颜色来表示它。

量化的主要目标是减少表示原始参数所需的位数(颜色),同时尽可能保持原始参数的精度。

常见数据类型

首先,让我们看看常见的数据类型,以及使用它们而不是32位(称为_全精度_或_FP32_)表示的影响。

FP16

让我们看一个从32位到16位(称为_半精度_或_FP16_)浮点数的示例:

注意 FP16 可以取的值范围比 FP32 小得多。

BF16

为了获得与原始 FP32 相似的值范围,引入了 bfloat 16 作为一种"截断的 FP32":

BF16 使用与 FP16 相同数量的位,但可以取更广泛的值范围,并且经常用于深度学习应用。

INT8

当我们进一步减少位数时,我们接近了_基于整数的表示_而不是浮点表示的领域。为了说明,从 FP32 到 INT8(只有 8 位)会导致原始位数的四分之一:

根据硬件的不同,基于整数的计算可能比浮点计算更快,但情况并非总是如此。然而,使用更少的位通常会使计算更快。

对于每一次位数的减少,都会执行一个映射来将初始 FP32 表示"压缩"到更低的位数。

在实践中,我们不需要将整个 FP32 范围 [-3.4e38, 3.4e38] 映射到 INT8。我们只需要找到一种方法将我们数据(模型参数)的范围映射到 INT8。

常见的压缩/映射方法是_对称_和_非对称_量化,它们是_线性映射_的形式。

让我们探讨这些从 FP32 到 INT8 量化的方法。

对称量化

在对称量化中,原始浮点值的范围被映射到量化空间中围绕零的对称范围。在前面的例子中,注意量化前后的范围仍然以零为中心。

这意味着浮点空间中零的量化值在量化空间中恰好为零。

对称量化的一个很好的例子是所谓的绝对最大值(absmax)量化。

给定一个值列表,我们取_最高_绝对值(α)作为执行线性映射的范围。

注意 [-127, 127] 值范围表示受限范围。不受限制的范围是 [-128, 127],取决于量化方法。

由于它是以零为中心的线性映射,公式很简单。

我们首先使用以下方法计算比例因子(s):

  • 是我们想要量化到的字节数(8),

  • α 是_最高_绝对值,

然后,我们使用 s 来量化输入 x:

填入数值后,我们得到以下结果:

为了检索原始 FP32 值,我们可以使用先前计算的_缩放因子_(s)来_反量化_量化值。

应用量化然后反量化过程以检索原始值如下所示:

你可以看到某些值,如 3.083.02 被分配到 INT8,即 36。当你将值反量化以返回 FP32 时,它们会失去一些精度,不再可区分。

这通常被称为_量化误差_,我们可以通过找出原始值和反量化值之间的差异来计算。

通常,位数越低,我们倾向于有更多的量化误差。

非对称量化

非对称量化"与之相反,不是围绕零对称的。相反,它将浮点范围的最小值(β)和最大值(α)映射到量化范围的最小值和最大值。

我们将要探讨的方法称为"零点量化"。

注意0是如何移位的?这就是为什么它被称为"非对称量化"。在[-7.59, 10.8]范围内,最小/最大值与0的距离不同。

由于其位置发生了偏移,我们必须计算INT8范围的零点以执行线性映射。和之前一样,我们还必须计算一个"缩放因子"(s),但使用INT8范围的差值[-128, 127]

注意这比之前稍微复杂一些,因为需要计算INT8范围内的"零点"(z)来移动权重。

和之前一样,让我们填写公式:

要将量化后的INT8反量化回FP32,我们需要使用先前计算的"缩放因子"(s)和"零点"(z)。

除此之外,反量化很简单:

当我们将对称和非对称量化并排放置时,我们可以很快看出两种方法之间的区别:

注意对称量化的零中心性质与非对称量化的偏移。

范围映射和裁剪

在我们之前的例子中,我们探讨了如何将给定向量中的值范围映射到较低位的表示。虽然这允许映射向量值的全范围,但它有一个主要缺点,即"异常值"。

想象你有一个具有以下值的向量:

注意其中一个值比其他所有值都大得多,可以被视为异常值。如果我们要映射这个向量的全范围,所有小值都会被映射到相同的低位表示,失去它们的区分因素:

这是我们之前使用的absmax方法。请注意,如果我们不应用裁剪,非对称量化也会发生相同的行为。

相反,我们可以选择"裁剪"某些值。裁剪涉及设置原始值的不同动态范围,使所有异常值获得相同的值。

在下面的例子中,如果我们手动将动态范围设置为[-5, 5],所有超出该范围的值将被映射为-127或127,无论它们的实际值如何:

主要优势是"非异常值"的量化误差显著减少。然而,"异常值"的量化误差增加。

校准

在这个例子中,我展示了一种选择任意范围[-5, 5]的简单方法。选择这个范围的过程被称为"校准",旨在找到一个包含尽可能多的值同时最小化量化误差的范围。

对不同类型的参数执行这个校准步骤并不相同。

权重(和偏置)

我们可以将LLM的权重和偏置视为"静态"值,因为它们在运行模型之前就已知。例如, Llama 3的~20GB文件[26] 主要由其权重和偏置组成。

由于偏置(数百万)比权重(数十亿)少得多,偏置通常保持在更高的精度(如INT16),而量化的主要努力集中在权重上。

对于权重,它们是静态且已知的,选择范围的校准技术包括:

  • 手动选择输入范围的_百分位数_

  • 优化原始权重和量化权重之间的_均方误差_ (MSE)。

  • 最小化原始值和量化值之间的_熵_ (KL散度)

例如,选择百分位数会导致类似于我们之前看到的裁剪行为。

激活值

在LLM中持续更新的输入通常被称为"激活值"。

请注意,这些值被称为激活值,因为它们通常会通过某种激活函数,如sigmoid或relu。

与权重不同,激活值在推理过程中随每个输入数据而变化,这使得准确量化它们变得具有挑战性。

由于这些值在每个隐藏层之后都会更新,我们只有在输入数据通过模型时才能知道它们在推理过程中的值。

广义上讲,有两种方法来校准权重和激活值的量化方法:

  • 训练后量化 (PTQ)

  • 训练_之后_进行量化

  • 量化感知训练 (QAT)

  • 训练/微调_期间_进行量化

第3部分:训练后量化

训练后量化(PTQ)是最流行的量化技术之一。它涉及在模型训练之后对模型参数(权重和激活值)进行量化。

_权重_的量化使用对称或非对称量化来执行。

然而,_激活值_的量化需要对模型进行推理以获得它们的潜在分布,因为我们不知道它们的范围。

激活值的量化有两种形式:

  • _动态_量化

  • _静态_量化

动态量化

数据通过隐藏层后,收集其激活值:

然后使用这个激活值分布来计算量化输出所需的_零点_ (z) 和_比例因子_ (s) 值:

每次数据通过新层时都会重复这个过程。因此,每一层都有自己独立的_zs_值,从而有不同的量化方案。

静态量化

与动态量化相比,静态量化不是在推理过程中计算_零点_ (z) 和比例因子 (s),而是预先计算。

为了找到这些值,使用校准数据集并将其提供给模型以收集这些潜在分布。

收集这些值后,我们可以计算出在推理过程中执行量化所需的_sz_值。

在实际进行推理时,_sz_值不会重新计算,而是全局用于所有激活值的量化。

一般来说,动态量化往往更准确一些,因为它只尝试为每个隐藏层计算_sz_值。然而,它可能会增加计算时间,因为这些值需要被计算。

相比之下,静态量化虽然不太准确,但速度更快,因为它已经知道用于量化的_sz_值。

4位量化的领域

低于8位量化已被证明是一项困难的任务,因为随着每一位的损失,量化误差会增加。幸运的是,有几种聪明的方法可以将位数降低到6位、4位,甚至2位(尽管使用这些方法通常不建议低于4位)。

我们将探讨两种在HuggingFace上常见的方法:

  • GPTQ(完整模型在GPU上)

  • GGUF(可能将层卸载到CPU上)

GPTQ

"GPTQ"可以说是实践中用于4位量化最著名的方法之一。1[27]

它使用非对称量化,并逐层进行,使得每一层在继续下一层之前都被独立处理:

在这个逐层量化过程中,它首先将该层的权重转换为逆Hessian矩阵。这是模型损失函数的二阶导数,告诉我们模型输出对每个权重变化的敏感程度。

简单来说,它本质上展示了每层中每个权重的()重要性

与Hessian矩阵中较小值相关的权重更为关键,因为这些权重的微小变化可能导致模型性能的显著变化。

在逆Hessian中,较低的值表示更"重要"的权重。

接下来,我们对权重矩阵第一行的权重进行量化然后反量化:

这个过程允许我们计算量化误差(q),我们可以使用之前计算的逆Hessian(h_1)对其进行加权。

本质上,我们正在基于权重的重要性创建一个加权量化误差:

接下来,我们将这个加权量化误差重新分配到该行的其他权重上。这允许维持网络的整体功能和输出。

例如,如果我们对第二个权重.3(x_2)这样做,我们会加上量化误差(q)乘以第二个权重的逆Hessian(h_2)

我们可以对给定行中的第三个权重进行相同的过程:

我们迭代这个重新分配加权量化误差的过程,直到所有值都被量化。

这之所以如此有效,是因为权重通常彼此相关。因此,当一个权重有量化误差时,相关权重会相应地更新(通过逆Hessian)。

注意: 作者们[28] 使用了几个技巧来加速计算并提高性能,比如向Hessian添加阻尼因子、"懒惰批处理"和使用Cholesky方法预计算信息。我强烈建议查看 这个YouTube视频[29] 了解这个主题。
提示: 如果你想要一种旨在性能优化和提高推理速度的量化方法,可以查看 EXL2[30]

GGUF

虽然GPTQ是在GPU上运行完整LLM的一种很好的量化方法,但你可能并不总是有这种能力。相反,我们可以使用GGUF将LLM的任何层卸载到CPU上。2[31]

这允许你在没有足够VRAM时同时使用CPU和GPU。

GGUF量化方法经常更新,可能取决于位量化的级别。然而,一般原理如下。

首先,给定层的权重被分割成"超级"块,每个块包含一组"子"块。从这些块中,我们提取比例因子(s)和alpha(α):

要量化给定的"子"块,我们可以使用之前使用的_absmax_量化。记住,它将给定权重乘以比例因子**(s)**:

子"块的比例因子使用"超级"块的信息进行量化,而"超级"块有自己的比例因子:

这种分块量化使用"超级"块的比例因子(s_super)来量化"子"块的比例因子(s_sub)。

每个比例因子的量化级别可能不同,通常"超级"块的精度比"子"块的比例因子更高。

为了说明,让我们探讨几个量化级别(2位、4位和6位):

注意:根据量化类型,需要一个额外的最小值(m)来调整零点。这些与比例因子(s)的量化方式相同。

查看 原始拉取请求[32] 以了解所有量化级别的概述。另外,请参阅 此拉取请求[33] 以获取有关使用重要性矩阵进行量化的更多信息。

第4部分:量化感知训练

在第3部分中,我们看到了如何在训练_之后_对模型进行量化。这种方法的一个缺点是,这种量化并不考虑实际的训练过程。

这就是量化感知训练(QAT)的用武之地。QAT旨在__训练期间学习量化程序,而不是在训练后使用训练后量化(PTQ)对模型进行量化。

QAT往往比PTQ更准确,因为在训练过程中已经考虑了量化。它的工作原理如下:

在训练过程中,引入了所谓的""量化。这是首先将权重量化为(例如)INT4,然后再反量化回FP32的过程:

这个过程允许模型在训练、损失计算和权重更新期间考虑量化过程。

QAT试图探索""极小值的损失景观,以最小化量化误差,因为""极小值往往会导致更大的量化误差。

例如,想象一下如果我们在反向传播过程中不考虑量化。我们根据梯度下降选择损失最小的权重。然而,如果它在""极小值中,这将引入更大的量化误差。

相比之下,如果我们考虑量化,将在""极小值中选择一个不同的更新权重,量化误差会小得多。

因此,尽管PTQ在高精度(例如FP32)下具有较低的损失,但QAT在较低精度(例如INT4)下产生较低的损失,这正是我们的目标。

1位LLM时代:BitNet

我们之前看到的4位已经相当小了,但如果我们进一步减少呢?

这就是 BitNet[34] 的用武之地,它使用单个1位表示模型的权重,对给定权重使用**-11**。3[35]

它通过将量化过程直接注入Transformer架构来实现这一点。

请记住,Transformer架构被用作大多数LLM的基础,由涉及线性层的计算组成:

这些线性层通常以更高的精度表示,如FP16,并且是大多数权重所在的地方。

BitNet用它们称为BitLinear的东西替换了这些线性层:

BitLinear层的工作原理与常规线性层相同,根据权重乘以激活来计算输出。

相比之下,BitLinear层使用1位表示模型的权重,使用INT8表示激活:

BitLinear层,类似于量化感知训练(QAT),在训练期间执行一种"伪"量化,以分析权重和激活量化的影响:

注意:在论文中他们使用了γ而不是α,但由于我们在整个示例中使用了a,所以我使用的是a。另外,请注意β与我们在零点量化中使用的不同,而是绝对值的平均值。

让我们逐步了解BitLinear。

权重量化

在训练时,权重以INT8存储,然后使用一种基本策略(称为符号函数)量化为1位。

本质上,它将权重分布移动到以0为中心,然后将左侧的所有内容指定为-1,右侧的所有内容指定为1:

此外,它还跟踪一个值β(绝对值的平均值),我们稍后将用于反量化。

激活量化

为了量化激活,BitLinear利用absmax量化将激活从FP16转换为INT8,因为它们需要更高的精度来进行矩阵乘法(×)。

此外,它还跟踪α(最高绝对值),我们稍后将用于反量化。

反量化

我们跟踪了α(激活的最高绝对值)和β(权重的平均绝对值),因为这些值将帮助我们将激活反量化回FP16。

输出激活使用{α, γ}重新缩放,以将它们反量化为原始精度:

就是这样!这个过程相对简单,允许模型仅用两个值表示,要么是**-1**,要么是1

使用这个过程,作者观察到随着模型规模的增长,1位和FP16训练之间的性能差距越来越小。

然而,这仅适用于较大的模型(>30B参数),对于较小的模型,差距仍然相当大。

所有大型语言模型都是1.58位

BitNet 1.58b[36] 被引入以改进前面提到的扩展问题。4[37]

在这种新方法中,模型的每个权重不仅仅是**-11**,现在还可以取0作为值,使其成为三元的。有趣的是,仅仅添加0就大大改进了BitNet,并允许更快的计算。

0的力量

那么为什么添加0是如此重大的改进呢?

这与矩阵乘法有关!

首先,让我们探讨一下矩阵乘法的一般工作原理。在计算输出时,我们将权重矩阵乘以输入向量。下面可视化了权重矩阵第一层的第一次乘法:

请注意,这个乘法涉及两个动作,将单个权重与输入相乘,然后将它们全部相加。

相比之下,BitNet 1.58b设法避免了乘法操作,因为三元权重本质上告诉你以下内容:

  • 1: 我想添加这个值

  • 0: 我不想要这个值

  • -1: 我想减去这个值

作为结果,如果你的权重量化为1.58位,你只需要执行加法:

这不仅可以显著加快计算速度,还允许进行特征过滤

通过将给定权重设置为0,你现在可以忽略它,而不是像1位表示那样要么加要么减权重。

量化

为了执行权重量化,BitNet 1.58b使用了_absmean_量化,这是我们之前看到的absmax量化的一种变体。

它简单地压缩权重分布,并使用绝对平均值(α)来量化值。然后将它们四舍五入到-1、0或1:

与BitNet相比,激活量化是相同的,除了一件事。现在不是将激活缩放到范围[0, 2ᵇ⁻¹],而是使用_absmax量化_将它们缩放到[-2ᵇ⁻¹, 2ᵇ⁻¹]。

就是这样!1.58位量化(主要)需要两个技巧:

  • 添加 以创建三元表示[-1, 0, 1]

  • 权重的_absmean量化_

"13B BitNet b1.58在延迟、内存使用和能耗方面比3B FP16 LLM更高效"

因此,我们得到了轻量级模型,因为只有1.58个计算效率高的位!

结论

这就结束了我们的量化之旅!希望这篇文章能让你更好地理解量化、GPTQ、GGUF和BitNet的潜力。谁知道未来的模型会有多小呢?!

要查看更多与LLM相关的可视化内容并支持这份通讯,请查看我正在与Jay Alammar合著的书。它将很快发布!

资源

希望这是一个易于理解的量化入门!如果你想深入了解,我建议以下资源:

  • 一篇关于** LLM.int8()[38]

  • **量化方法的HuggingFace博客:你可以在 这里[39]找到论文。

  • 另一篇很棒的HuggingFace博客,关于** 嵌入[40]**的量化。

  • 一篇关于 Transformer数学101[41]的博客,描述了与transformer计算和内存使用相关的基本数学。

  • 这个[42]和 这个[43]是两个很好的资源,用于计算给定模型所需的(V)RAM

  • 如果你想了解更多关于QLoRA5[44]的信息,这是一种用于微调的量化技术,在我即将出版的书中有广泛的介绍: 大型语言模型实践[45]

  • 一个真正 令人惊叹的YouTube视频[28],以非常直观的方式解释GPTQ

参考链接

1. 如何表示数值: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§how-to-represent-numerical-values
2. 内存限制: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§memory-constraints
3. 常见数据类型: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§common-data-types
4. FP16: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§fp16
5. BF16: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§bf16
6. INT8: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§int8
7. 对称量化: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§symmetric-quantization
8. 非对称量化: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§asymmetric-quantization
9. 范围映射和裁剪: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§range-mapping-and-clipping
10. 校准: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§calibration
11. 权重(和偏置): https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§weights-and-biases
12. 激活: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§activations
13. 动态量化: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§dynamic-quantization
14. 静态量化: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§static-quantization
15. 4位量化的领域: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§the-realm-of-bit-quantization
16. GPTQ: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§gptq
17. GGUF: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§gguf
18. 1位大语言模型时代:BitNet: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§the-era-of-bit-llms-bitnet
19. 权重量化: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§weight-quantization
20. 激活量化: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§activation-quantization
21. 反量化: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§dequantization
22. 所有大型语言模型都在1.58位: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§all-large-language-models-are-in-bits
23. 0的力量: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§the-power-of
24. 量化: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#§quantization
25. IEEE-754: https://en.wikipedia.org/wiki/IEEE_754
26. Llama 3的~20GB文件: https://huggingface.co/meta-llama/Meta-Llama-3-8B/tree/main
27. 1: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#footnote-1-145531349
28. 作者们: https://arxiv.org/pdf/2210.17323
29. 这个YouTube视频: https://www.youtube.com/watch?v=mii-xFaPCrA
30. EXL2: https://github.com/turboderp/exllamav2
31. 2: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#footnote-2-145531349
32. 原始拉取请求: https://github.com/ggerganov/llama.cpp/pull/1684
33. 此拉取请求: https://github.com/ggerganov/llama.cpp/pull/4861
34. BitNet: https://arxiv.org/pdf/2310.11453
35. 3: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#footnote-3-145531349
36. BitNet 1.58b: https://arxiv.org/pdf/2402.17764
37. 4: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#footnote-4-145531349
38. LLM.int8(): https://huggingface.co/blog/hf-bitsandbytes-integration
39. 这里: https://arxiv.org/pdf/2208.07339
40. 嵌入: https://huggingface.co/blog/embedding-quantization
41. Transformer数学101: https://blog.eleuther.ai/transformer-math/
42. 这个: https://huggingface.co/spaces/NyxKrage/LLM-Model-VRAM-Calculator
43. 这个: https://vram.asmirnov.xyz/
44. 5: https://newsletter.maartengrootendorst.com/p/a-visual-guide-to-quantization#footnote-5-145531349
45. 大型语言模型实践: https://www.amazon.com/Hands-Large-Language-Models-Understanding/dp/1098150961

幻想发生器
图解技术本质
 最新文章