众所周知,Transformer 是赋予模型重要特性及有趣结构的核心,从而支撑了各类应用。Transformer 与多层感知机的关键区别在于存在注意力层,该层发挥着神奇作用。在注意力层中,查询(Query)与键(Key)进行内积运算,计算 Softmax 并使用其值对前一层嵌入进行重加权。通过多次重复此过程,模型能神奇地通过预测下一个词元获得优异结果。
本次讲座主要探讨如何理解这一机制,基于两篇论文:一篇是入选 ECCV 2023 的《Scan and Snap》,另一篇是入选 ICLR 的后续论文《Drama》。我们从单层注意力设置入手,旨在通过简单设定理解数学公式与结构,从而更好地把握多层 Transformer。在单层设置中,输入为上下文词元序列,最后一个词元作为查询,进行自注意力计算。
得到各词元的概率分布及注意力分数后,利用这些分数作为权重计算输出特征。该特征经过归一化、前馈网络层及 Softmax,用于预测下一个词元。这是一个简单的端到端数学结构。若直接写出公式,会涉及大量参数如 WQ、WK 和 U,导致梯度计算复杂混乱。因此,我们引入了两个重要技巧。
首先,通过独立变量对问题进行重参数化,这对理解多层 Transformer 至关重要。我们将众多变量重参数化为 y 和 z,其中 y 代表顶层解码器权重,z 代表自注意力矩阵的成对逻辑值。这使得动态分析变得更容易,并能得出一些结论。这是主要的第一步,我们随后将推导 y 和 z 的动态方程。
在介绍 Drama 后,公式将简化。我们先看结论,即 Transformer 属性的来源。《Scan and Snap》的主要假设包括:无位置编码(因处理较难且无位置编码也能取得合理性能)、序列长度趋于无穷大、解码器 Y 的学习率大于自注意力层 Z 的学习率,以及一些技术假设。
在分布假设上,我们将序列分为 k 类,每类包含两类词元:仅在一类中出现的“独特词元”和在多类中出现的“公共词元”。对于独特词元,给定序列索引下该词元出现的概率仅在一类中大于零;而公共词元则出现在多个序列类中。基于此,我们探讨自注意力层的行为及 Transformer 动态的整体图景。
我们引入关键统计量“CL 标题”,即共现概率与注意力矩阵成对指数项的乘积。对于独特词元,由于共现概率仅在一类中非零,其 CL 标题仅在一类中非零,呈现明显模式。对于公共词元,其出现在多个序列类中。分析显示,公共词元的注意力分数梯度为负,随时间推移逐渐减小。
这意味着 z 随时间减小,因为 z 对时间的导数小于零。这对于出现在多个序列类中的公共词元基本成立。另一方面,对于独特词元,其对应的注意力逻辑值 z 会随时间增长。图表展示了这一增长过程,所有独特词元的注意力分数均会上升。
增量更新。我们的注意力分数也会随着最终输出 c 的紧密度增加而上升。因此,从这两点可以看出,注意力机制有点像可学习的 TF-IDF,对吧?如果人们在 Transformer 时代之前从事过自然语言处理工作,可能听说过这种 TF-IDF 公式。它意味着你要找到那些具有高频率的词,同时也希望找到具有逆文档频率的词,对吧?
第一项讨论的是每个类别中非常重要的词,而第二个标准基本上要求模型过滤掉在多个文档中过于常见的 token,对吧?例如,在所有文章和所有常见词汇中,它们缺乏信息量,因此在进行文档分类决策时应该抑制它们。另一方面,如果你拥有特定类别的特定 token,那么我们应该关注它们,对吧?
例如,如果你谈论体育和梅西,那么梅西对于体育来说是一个非常重要的 token,并且存在连接,你可以利用它来进行更好的文档分类。此外,我们实际上可以对注意力分数的增长率进行量化。ZML 基本上是自注意力矩阵的一个元素,这实际上是时间的函数。
给定序列类别和注意力条件概率 L 较大时,它会增长得更快,我们实际上可以表征它为何增长得更快。因此,我们可以有一个定理。该定理告诉你,两个不同 token 之间的比率,它们增长了多少以及增长的速度。
图表也显示,如果你拥有与查询具有极高共现性的不同 token,那么它的增长速度将远快于那些仅偶然与该 token 共现但概率不高的不同 token。在进行训练时,你会看到这种非常显著的跳跃。
在某种意义上,这被称为上下文稀疏性,因为随着时间的推移,你会看到经过归一化后的注意力分数 c 实际上会变得越来越稀疏。因为赢家通吃,富者愈富,而穷者愈穷,对吧?
随着时间的推移,你可能会看到一个或两个突出的情况,这就是为什么你在训练过程中看到注意力变得越来越稀疏的原因。我们称之为上下文稀疏性的原因是,这取决于查询。对于不同的查询,你会看到非常不同的曲线。
对于不同的查询 token,情况会像这样。从不同的查询 token 来看,也许另一个 token 会与那个特定 token 具有高共现性。然后你会看到非常不同的模式。这就是查询依赖的稀疏性。
最后,我们实际上展示了注意力存在两阶段效应。人们可能会根据这张图想知道,随着时间的推移,你会看到与查询具有高共现性的 token 的增长率越来越高,最终你会看到赢家通吃的效应。但实际上并非如此。
在我们的分析中,我们最终将展示存在两个不同的阶段。一个称为注意力扫描(attention scanning),赢家通吃效应就发生在这个阶段。另一方面,第二个阶段称为注意力快照(attention snapping)。
在这个阶段,一切都会稍微慢下来,最终达到饱和。一旦你看到富者愈富的效应,经过一段时间后,注意力模式就会冻结,变得有点像少数派通吃的情况,但这并不是赢家通吃。
这就是扫描和快照论文所展示的整体画面。基本上这就是主要画面,我们有一些不同的模拟来证明这确实是事实。这里有一些用于手术式分析的整体策略。
如果人们感兴趣,这里有一个非常简单的策略来证明这一点。首先,我们要利用无限序列长度的优势,基本上将所有项转化为包含概率分布的统计项。这是第一步。
第二步,因为我们假设 Y(解码器)的学习率远快于 Z(自注意力矩阵)的学习率,那么在分析解码器的动态时,你可以基本上将自注意力矩阵视为常数。
一旦我们有了那个很好的方程,它告诉你梯度如何反向传播到状态(注意力层)与输入到解码器的数据相关,我们可以将其代入自注意力层,然后分析自注意力层中发生的事情。
基本上,这就是如何分析单层 Transformer 的两层结构。我们进行了一些非常简单的真实实验。例如,在 WikiText2 上,如果你拥有这种学习率结构,那么随着时间的推移,你会在注意力中看到非常稀疏的模式。
如果你在实践中对训练 Transformer 做了大量工作,你也会看到这种学习模式的变化。这就是扫描快照论文,非常简单。然后我们讨论了如何改进扫描快照,以及如何摆脱这些假设。
我们有一些令人烦恼的假设,比如没有嵌入向量,没有残差连接。解码器需要比 Transformer 注意力学习得更快,这在实践中从未发生过。此外,我们只有单层分析。
那么,如何摆脱它们呢?下一步是引入名为 DRAMA 的工作。这是我们第二篇后续论文,旨在比之前的论文更好地理解这些动态。在那篇论文中,我们实际上发现了 MLP 下层与自注意力层之间训练动态的一些非常好的特性。
将它们结合起来形成一个称为修改后的 MLP 的层。该层实际上捕获了两层的动态,同时更加简单。如果你同时考虑自注意力和 MLP 层,基本上就是……
对 Transformer 单层注意力机制动态演化规律的大致构想。我们基本上将 Transformer 的一层向下拖拽,并放置大量符号以分析其内部机制。现在考虑到此处额外的残差连接(ResNet connections),这些残差连接在之前的分析中缺失,但现在我们可以将其加回,展示其实际发挥的作用,并利用这些非线性激活函数。这里的 $\phi$ 即为非线性项。在 Decoder 层中,与我们之前类似的论文不同,那里没有非线性项,直到 Softmax 之前基本是线性的,这就是区别所在。因此,我们实际上能够展示一些良好的性质。
此外,这里还有嵌入矩阵 $U$。对于嵌入矩阵,我们基本假设这些嵌入向量彼此正交,且这种正交性不随时间改变。这确实是审稿人提出质疑的假设,因此我们有一张图表展示在实践中这确实是成立的。当我们绘制像 PyTear 等模型在不同层之间嵌入向量的相似度时,我们也测试了其他模型,结果看起来也非常符合。基本上,图表显示横轴是训练动态中的小批量(mini-batches),纵轴是余弦相似度。
余弦相似度在零到一之间变化,一表示完美对齐,零表示彼此正交。你在图中看到的是,在训练过程中,余弦相似度并没有显著增加,基本保持在零点零三左右。这意味着即使对于不同的层,嵌入向量也几乎彼此正交。这里的每条曲线对应不同的层,层数由曲线的颜色表示。因此,这表明正交性假设在近似意义上是成立的。
然而,我们尚未分析嵌入的动态变化,这可能是下一篇论文的主题。基于这些假设,我们会看到 MLP 下层与自注意力层之间存在联合动态。你可以从下层权重的幅度计算出自注意力。这意味着一旦拥有该方程,你就可以忽略对自注意力层的训练,只需将此方程代入动态模型,即可得到相应的结果。
该方程讲述了注意力机制和下层 MLP 的故事。你可以利用该方程分析 Transformer 的动态,这就是基本思路。这使得事情变得简单得多,且不需要假设 Decoder 层的训练速度远快于自注意力层,你不再需要那个假设了。这里有一些幻灯片试图比较 Scan、Snap 和 Drama。这是为了回答学生提出的问题而添加的额外幻灯片。
这里有一个通用公式,试图将两者结合起来。我们有一个统一的通用公式 formulation 将这两者结合。这里有一些符号,以及两篇论文之间的共同假设。首先,下层权重 $W$ 和自注意力层权重 $Z$ 都是可训练参数,它们可以被训练。在这两项工作中,我们都没有考虑 $W_K, W_Q, W_V$,而是将整个 $Z$ 矩阵视为可训练参数。
这与实际情况有所不同。其次,嵌入 $U$ 是固定的且列正交。这也是我们为两篇论文所做的另一个假设。第三,输入 token 向量实际上是独热(one-hot)列向量,这样我们可以计算频率。这对于第一层肯定是成立的,因为每个 token 都由独热表示编码,但对于多层和中间非线性而言,这可能不一定成立。
Scan、Snap 和 Drama 之间的区别在于设置可能非常不同。例如,在 Scan 和 Snap 中,你可能有额外的归一化(L2),并且必须假设激活函数是线性的,且 $W$ 的学习速度远快于 $Z$。而在 Drama 中,我们的设置不同。也许 $\phi$ 是恒等映射,没有归一化,但在非线性方面,你可以使用线性或非线性激活函数,还有许多其他不同的方向。
这是关于第一个定理推导的一页幻灯片。我不想详细展开,只是将其作为定理一的总结。如果人们感兴趣,可以自行查看。这比论文中给出的证明要简洁得多,我们将在最终版本中更新这一点。那么,如果拥有这种联合动态,Drama 会发生什么?这是对动态的验证,因为在自注意力层中我们做出了一些假设,我们要确保假设成立。
一旦拥有这种联合动态,我们就可以回到 Scan 和 Snap 的设置中,其中激活是线性的,看看它是否产生与 Scan 和 Snap 相同的预测。答案是肯定的,我们可以得到非常相似的预测。预测基本上表明注意力将变得更加稀疏,这与 Scan 和 Snap 一致。具有最高 token 判别性乘以相干性的组件,如果该项在幅度上最高,那么它的曲线将比其他曲线更快地饱和。
这与 Scan 和 Snap 一致。但更有趣的是,如果你能将 Drama 扩展到非线性激活,例如……
激活函数是非线性的,那么之前的扫描步骤论文就无法提供有效信息。但实际上,我们可以观察到与非线性激活相对应的更有趣的行为。注意力机制首先会变得更加稀疏,这正是散点图论文所预测的结果;但同时,在后续的激活阶段,它会重新变得密集。这基本上就是两者的区别:非线性激活与线性激活下的注意力模式截然不同。在线性激活情况下,注意力只会变得越来越稀疏,直到饱和;而在非线性情境下,后期注意力会重新变密。
我不打算深入探讨其中的数学细节,但我们首先希望验证这些理论是否与真实实验一致。我们在两个真实世界的文本数据集——WikiText 2 和 WikiText 103 上训练了多层 Transformer 模型,旨在观察是否会出现与理论预测完全相同的曲线。特别是在第一层,如果使用非线性训练单层 Transformer,你会看到注意力先下降然后回升,这与理论绘制的曲线非常相似。
如果在多层中进行训练,也会观察到非常相似的曲线,特别是在顶层,你会看到注意力先下降后回升。这非常有趣。我们随后希望深入理解这种现象的原因,因为这些行为并不直观,尤其是对于单层而言。单层通常被认为是一次性完成特征提取,为什么需要在后期拾取那些不显著的特征呢?
首先,注意力变稀疏的机制与扫描步骤中的机制相同:与查询共同出现的 token 会被优先拾取,导致注意力上升,而其他注意力保持不变或下降。这就是为什么注意力熵会降至极低数值。然而,过一段时间后,注意力分数会回升,熵也会增加。这是因为模型开始拾取那些不显著但随时间推移仍具韧性的特征和 token。
这并非在第一步就发生,因为这里的单位是 mini-batch K(千个 mini-batch)。基本上,它必须从最初的千个 mini-batch 开始下降,之后才会回升。是的,我认为具体的尺度可能并不重要,因为通过调整学习率,你可以得到不同的尺度。在与其他模型的真实实验中,我们也观察到了类似的行为。
我们之所以观察到这种现象,是因为我们有一个假设将在后面讨论这些属性。基本上,这种属性对单层无用,因为在单层中,为什么不一次性学习所有特征而不具备这种有趣的属性呢?但这可能在多层中是有用的。其在多层中有益的原因,我们需要考虑分层的数据表示。
我们希望通过数据学习分层的数据表示。在这种表示中,你只能看到最终标签(顶层)和最低层的 token,而无法直接看到内部发生的情况。存在支配数据生成过程的潜在变量,但我们对此一无所知。然而,我们确实希望训练 Transformer 模型,使其能够自动学习数据集中的潜在表示。
我们假设,在 Transformer 中观察到注意力回升的原因,是因为模型实际上可以在此处学习潜在表示。首先,我们可以证明一个定理:如果两个 token 在层级结构中非常接近,它们共同出现的概率将非常高,几乎等于一。但如果两个 token L' 和 M 在层级中相距甚远,它们的共同出现概率将很低,接近于零。
这里有一个方程描述了这种行为:H 基本上是这两个 token L 和 M 的公共潜在祖先的高度。对于 L 和 M,它们的公共潜在祖先高度 h 很小,代入后概率近似为一。如果使用相同的公式计算相距甚远的 L' 和 M,它们的公共潜在祖先高度几乎等于层级总高度 L,此时概率几乎为零。
首先,我们拥有这一假设,即分层生成模型具有这种有趣的属性。请注意,这一属性与 Transformer 本身无关。接着我们思考 Transformer 应如何学习它。我们认为,首先学习共同出现频率高的 token,然后学习共同出现稀疏的 token。这种机制对浅层和深层潜在分布都有效。
对于深层潜在分布,我们首先学习 m 和 r 的关联,以及 m' 和 r' 的关联,因为它们根据之前的层级分析彼此高度相关。因为首先学习了这两组关联,模型自动隐式地构建了一个层级结构,可以在顶层再次组合。这样,你基本上避免了学习 m 和 r' 的关联,尽管它们可能有一定共同出现,但这种共同出现并不重要,可以通过分层学习间接习得。
这实际上给了你 Transformer 应以此方式学习特征的直觉。另一方面,如果数据是由某些浅层潜在分布生成的,情况则有所不同。
层级结构并不多,我们只看到非常直接的分布。那么 Transformer 的学习会发生什么呢?Transformer 首先会学习那些高频出现的 token,比如 m 和 l。但最终,它会学会 m 和 l' 之间的对应关系,对吧?因为这两者之间仍然存在某种对应关系,尽管可能非常微弱。基本上,注意力机制这一相同机制,能够在不了解数据内部结构的情况下,同时学习深层潜在分布和浅层潜在分布。
这基本上为你提供了关于 Transformer 为何能在不了解底层分布的情况下完成许多有趣任务的见解。它会自动适应数据的结构。这基本上解释了为什么我们会看到注意力机制先下降然后再上升。回到图表中,你会看到有趣的行为。如果你训练相同的模型,使用相同的数据集,对吧?首先训练这一层模型,即单层的 Transformer 模型,你会看到非常深、非常有趣的结构。
这非常明显。但是,如果 Transformer 的层数变多,即拥有更深的 Transformer,那么在较低层中,它们基本上会下降,但没有回升。而在顶层,仍然存在一种类似底部反弹的属性。这种情况的原因也可以用这一理论来解释。如果你有多层 Transformer,那么你首先学习的是那些高频共现的项。
一旦你学会了这些,你就不需要再次学习 A 和 NPR 之间微弱的共现关系,因为你不需要学习这两者之间的共现。因此,你就没有这种反弹属性。因为这种反弹属性已经被之前的机制解释掉了。这就是为什么在使用多层 Transformer 学习数据时,你不会在较低层看到曲线在之后反弹。
我认为目前这是我脑海中的一种理论,但我们尚未测试其他可能的解释。我明白。是的,我目前没有意识到有其他论文提出来解释这一点。是的,目前,但我的意思是,看看是否有其他替代理论会很有趣。是的,这只是扩展的一种方式。有没有办法生成一些合成的层级数据来证明这一理论?
是的,我们确实在一些一次性实验中这样做了。因为对于这一理论,一个可能的含义是,随着时间的推移,你会在 Transformer 的不同层中学习这些潜在变量,这在我们的分析中确实是正确的。例如,如果我们生成合成实验中的层级数据,你可以使用 Transformer 来学习它。你实际上会看到 Transformer 的隐藏层与潜在变量之间几乎 100% 的相关性,尤其是在前几层。你可以在论文中看到表格。
首先,这里的因果关系并不相关。我们不知道因果关系是否会在此发挥作用,因为我们只分析了相关性,没有因果关系。是的,但确实看起来它会先学习强注意力、强相关性,而这种强相关性可能意味着因果关系。因为如果你看到这两个 token 经常一起出现,那么它们之间可能存在真实的关联。
正如我们之前解释过的,如果你只用浅层 Transformer 训练数据,你会看到非常明显的反弹。如果你训练深层 Transformer,那么较低层一旦下降,就不会再反弹,因为反弹意味着较低层试图学习弱相关的特征。如果这些特征已经被顶层解释掉了,较低层就不需要再学习它们了。这就是为什么它只下降,而不再上升。
我的问题是,如果你在训练一三个 epoch 后解冻它们,你认为较低层是否会达到相同的水平,即反弹并停留在那里,还是你认为它会再次下降,而较高层会怎样?这是一个非常有趣的实验建议。是的,我认为有可能你会看到较低层反弹,然后再次下降。实际上,我在某些配置中看到了这条曲线。
这确实很有趣。还有其他实验表明,通过改变不同的学习率,你会看到非常不同的训练曲线。显示出这种反弹属性的训练曲线具有最高的验证准确率。这意味着这可能是学习数据的正确方式。与其他类型的学习率相比,你可以在论文中查看这些实验,我们尚未展示这一点。
这取决于你如何定义因果关系。因果关系可能意味着如果第一个发生,第二个就会发生,反之则不然。因为这是对称的,对吧?如果是这种情况,那么你可能需要设计属性,以强制注意力矩阵也具有相同的属性,诸如此类。这是可能的。我认为这是一个非常好的问题。
我们在实践中尝试了我们的参数化,即 Y 和 Z 参数化。结果是可以学习,但性能显然不如原始 Transformer。我们实际上有一个称为 YZ Transformer 的模型,即我们之前展示的 YZ 参数化。你可以实际训练它三层;它确实有效。但是当你训练多层时,它的效果并不好。这是因为嵌入的力量。
在 YZ Transformer 中,没有嵌入。嵌入全部放入这个 Z 矩阵中。Z 矩阵非常大,是词汇表大小乘以词汇表大小。但是这个巨大的矩阵在实际训练中可能无法很好地训练。在实践中,我们并不真正训练这个巨大的矩阵,而是训练嵌入以及权重,以基本模拟这个巨大的注意力矩阵。
矩阵。从某种意义上说,这要高效得多。因此,理论尚未解释这一方面,但希望未来我们能解释或说明嵌入矩阵的注意力动态情况。是的,所以我们基本上必须将其分解为几个部分,并逐一分析。是的,我认为这是一个很好的问题,因为我们之所以对第二个快照做出假设,是因为公式略有局限。
因此,你确实需要分析两种极端情况,对吧?要么一个标记出现在多个类别中,要么一个标记只出现在一个类别中,对吧?但实际上,中间情况还有很多。比如,一个标记在很多情况下出现,90%属于一个类别,但10%属于其他类别。那会发生什么?
戏剧性(Drama)的妙处在于,一旦你有了这个公式,这种属性就会自然产生。这种属性取代了常见标记与独特标记的对比。现在,我们有了一个涵盖所有标记的连续谱系,对吧?所以,如果这个量的幅度很高,那么这就是独特标记。如果这个量几乎为零,那么这就是常见标记。
是的,所以这里有一个谱系。你不再需要那个假设了。是的,这就是公式的好处。是的,所以你仍然有相干性和判别性。所以这与快照中的情况类似,但现在它变成了一个自然项,该项不需要特别处理。
好的,好的。所以我们在四十分钟内主要覆盖了两篇零样本论文。我认为在接下来的二十分钟里,我们将讨论更多的实证工作。所以我将跳过所有公式细节。希望人们已经足够了解这些内容。是的,我认为这里有很多问题是很棒的。通常,理论很难理解,但讨论未来的工作可能很有趣。
当然,这里未来的工作是我们要进行嵌入反向分析,对吧?在这两篇论文中,我们基本上假设嵌入是固定的,并且彼此正交。虽然如果你检查实证结果,这是真的,但这仍然不理想,因为嵌入也应该在训练过程中学习。但我们还没有测试过。我们还没有真正分析过嵌入的情况,对吧?
这有点可惜,对吧?但会有下一篇论文试图解决这个问题,位置编码也是另一个方面,对吧?所以我们也想谈谈潜在概念学习的动态,对吧?因为在多层设置中,我们基本上有一个关于这应该如何学习的概念,但没有具体的定理告诉你这个潜在向量是如何随时间学习的。但这非常棘手,很难处理。
好的,所以我要跳过这部分。这是另一张不相关的幻灯片,谈论由Drama产生的一些有趣属性。我要跳过它。所以这告诉你,MLP层中的一个向量可以编码多种不同的模式。这被称为模式叠加。这实际上已经被许多实证工作观察到,也被Anisotropic的一篇论文所强调。
但在Drama中,我们实际上也可以分析这一点,并表明如果你从头开始训练,遵循训练动态,这确实是可能的。但我要跳过它。好的,让我们进入第二部分,这是基于注意力属性的应用,主要是注意力稀疏性。为此,我们有一堆论文试图利用稀疏性来使推理更快。
所以希望从现在开始,我们谈论的是实证结果,希望观众的认知负担大大减轻。获取非常简单,对吧?所以我们只想保留注意力MLP中高激活的标记,并利用它来加速大模型的推理。是的。那么你在实证中看到的就是,对于每个前向路径,你看到很多头没有被激活,你也看到很多MLP层的激活也没有被激活。这实际上不太好,因为这意味着交叉注意力权重被白白加载了。
为了解决这个问题,我们提出了所谓的DJW。那篇论文基本上告诉你,如何预测在前向推理期间哪些头没有被激活,对吧?例如,头42、43没有被激活。它基本上在标记之间给出均匀分布,而头42和44则有非常清晰的模式。它们在分布方面有很清晰的焦点。你如何预测这一点?
所以我们实际上为每一层、每一个头以及每一次激活学习了一种非常漂亮、非常简单的预测器,关于哪些头和哪些MLP中间层应该被激活,对吧?所以我们基本上使用它来预测这种上下文稀疏性,并利用它使前向传播更快。这很简单,对吧?
我要预测这一点的原因是,如果我们在MLP层中知道只有第二和第六个(前六个)激活会被激活,那么我们只需要加载这两个权重的相应行和列。这种加载要快得多,因为你加载的权重数量更少。我们都知道,在GPU上,将内存加载到缓存非常慢,可能需要几百个GPU周期,而实际计算通常只需要几个周期,所以慢得多。
所以如果你能加载更少的权重,你实际上会有更快的前向传播速度。所以你可以这样做,你基本上可以做所有的工程工作,这就是最终的性能,对吧?所以我们可以使这种前向传播比不同的基准测试更快,对吧?所以如果你将它与Hugging Face和Fast Transformers进行比较,它的延迟确实更低,对吧?
这基本上就是这些想法,它与量化兼容,并且对于较小的批量大小特别有用。我们还有一篇名为H2O的论文,试图利用稀疏注意力进行快速推理,对吧?我们都知道,如果你计算注意力,实际上是n平方,对吧?所以基本上,对于每一个你想计算注意力的新标记,你必须遍历所有以前的标记,它是n平方。但问题是,我们真的需要……
需要所有之前的 token 吗?答案其实是否定的。如果我们画出这种分布,看看有多少 token 具有高激活值,有多少 token 具有低激活值,你会发现注意力分数的分布与共现非常相似。正如我在之前的幻灯片中所讨论的,这也是两者之间相关性的良好经验证据。此外,我们发现如果移除那些获得大量注意力的 token,下游任务的性能会急剧下降。这些在前向传播中出现频率高且获得大量注意力的 token,我们称之为“重击者”(heavy hitters)。
如果在推理中使用这些重击者,性能表现良好;如果移除它们,性能则非常糟糕。因此,自然的算法是只保留重击者,而移除那些注意力分数极低的 token。这种注意力算法被称为 H2O(Heavy Hitter Rules),本质上是一种局部贪心算法。在每一个解码器步骤中,你累加之前 token 的分数,并基本丢弃那些在所有先前运行中累积注意力分数最低的 token。你只保留一定预算的 KV 缓存 token,移除那些累积注意力分数低于阈值的 token。
这个想法非常简单,而且实际上能看到非常好的性能。例如,你只保留 20% 的 KV 缓存 token,但在多个基准测试中,性能几乎保持不变。如果只保留局部 token,性能会大幅下降;但如果只保留高注意力 token,在丢弃超过 80% 的 KV 缓存之前,性能一直很好。这不仅节省了内存,因为不需要保留 KV 缓存,还使推理速度快得多。
我们还发现它有其他好处,比如能增加创造性,因为它移除了一些可能限制创造性的 token。一个自然的问题是:这些重击者究竟是什么?我们进行了进一步分析,这导致了一篇名为《Attention Sink》(注意力汇)的论文,也称为 Streaming LM 论文,该论文已被今年的 ICLR 接收。我们基本在问:这些注意力重击者是什么?结果发现,许多重击者实际上是 Transformer 中的前几个 token,它们占据了大部分注意力分数,比例高达 50%,非常高。
那么,这会导致什么结果呢?我们提出假设:在许多情况下,我们可能不需要注意力机制将概率归一化到 1。但由于 Softmax 规则,注意力分数必须总和为 1。因此,它们基本上通过为初始的几个 token 分配多个极强的注意力分数来实现这一点。结果发现,这些前几个 token 的具体内容并不重要,你可以用特殊 token 替换它们,困惑度(perplexity)非常相似。
然而,如果移除前几个 token,模型就会崩溃,困惑度会飙升到五千左右,这意味着模型输出的是垃圾信息。因此,前几个 token 很重要,但重要的是它们的位置,而不是内容。这一发现非常有趣,我们后来发现,如果只保留前几个 token,你可以无限期地与模型进行对话,而不受上下文窗口的限制。这对于大规模模型的经验分布和部署非常重要。
这就是 Streaming LM 论文。该论文引起了外界的广泛关注,人们对此评价很高。该工作的某些变体已部署在硬件设备和库中。这里有一个非常简单的想法:当生成下一个 token 时,你首先保持一个固定长度的 KV 缓存预算。如果你的 token 生成超过了 KV 缓存预算,那么你就移除中间的这些 token。但你保留最近的 token 和初始 token,并保留它们在缓存中的注意力位置,而不是在原始窗口中的位置。
这基本上赋予了模型无限对话的能力。使用 Streaming LM,你将拥有无限对话,且所有文本都是合理的。当然,如果你不使用 Streaming LM,那么要么因为必须保留非常长的 KV 缓存序列而耗尽内存,要么如果你截断所有之前的 token(包括初始的前几个 token),模型就会突然崩溃,并在前几个 token 超出预算窗口后输出垃圾信息。
这非常有趣。我们在许多不同场景中测试过,发现我们的 Streaming LM 能提供非常稳定的困惑度,这意味着输出非常有意义。同时,它节省了内存,无论上下文窗口如何,随时间保持恒定内存。你只需要保持预算并保留前几个 token。这样,你就可以无限期地与大型模型聊天。这是那里有趣的特性。
我们还有其他一系列实验。你可以看到,它可以将模型扩展到四百万个 token,甚至更多,且困惑度保持不变,这是很好的。我们还与其他基线进行了比较。你也想了解前几个 token 发生了什么。如果将这些前几个 token 视为可学习的,会发生什么?你可以看到,可学习的 token 实际上做了同样的事情,而且效果甚至更好一点。
你在开头有一个专门的 token 称为同步 token(sync token),并且你保持同步 token 为零嵌入或可学习嵌入。这分别对应于零同步和可学习同步。你可以看到,在同步 token 存在之后,困惑度突然……
概率变得非常低,你实际上可以与模型进行聊天,而不会遇到上下文窗口长度的问题。是的,所以我们还看到了来自 Meta 的并发工作。有趣的是,我们不同部门之间没有交流,当我们提交论文时,看到了来自不同团队的非常相似的想法,他们也在视觉 Transformer 中发现了非常相似的结构,这被称为视觉 Transformer 需要寄存器(Registers)。寄存器对应于注意力汇聚点(Attention Sinks)。
当然,这实际上并没有解决长上下文问题。它只是丢弃令牌并保留概率。但如果你想进行某种系列操作,比如密码检索,如果对应答案的令牌被丢弃,它将无法给出正确答案。对吧?它基本上就是保留概率。这意味着它会给出合理的答案,但可能无法检索到被丢弃的信息。这基本上就是其局限性。希望未来我们也能做到这一点。
最后,基本上,我们想介绍另一篇试图解决长上下文窗口问题的论文。基本上是通过微调来实现。这基本上是一种可能的方案。哦,抱歉,这实际上是这篇论文。是的,就是这篇论文。在此之间,有一个流式 HTO,意味着你想将流式 RM 与 HTO 方法结合起来,对吧?
如果你思考一下流式 RM,它实际上是 HTO 的一种特殊情况。因为 Transformer 只保留前几个令牌,而两者会根据它们的注意力分数选择令牌。你将两者结合,实际上会给你更好的性能。同时,你将保持无限聊天的特性。这是我最近的更新。所以,我们将使用所有这些改进来实现快速推理。
最后有一种方法,有一篇名为《扩展上下文窗口》的论文。这实际上是一篇一直存在于预印本版本的论文,因为在发布两天后,我们在 Reddit 上看到人们有更好的想法来解决这个问题。所以我实际上说两天,对于这种情况应该是三十个小时左右。所以我们决定不提交这篇论文,因为竞争太激烈了。
是的,这实际上是一篇试图通过预训练来扩展上下文窗口的论文。我们都知道,预训练之后上下文窗口是无法改变的。例如,对于 Llama 版本,Llama 模型的上下文窗口是 2K。如果你尝试在 2K 之外使用它,它会突然给你垃圾信息。这基本上就是问题所在。
那么,我们如何扩展它呢?我们显然可以用更长的文本进行微调,但微调需要大量的资源和许多批次。所以我们实际上发现,通过改变 Llama 模型中的单个参数,你可以使微调更加高效。对吧?这实际上非常简单。我们基本上说,我们基本上改变嵌入,即位置嵌入的缩放比例,并将其缩放回原始大小。
例如,你的模型是 2K,如果你想将模型扩展到 4K,会发生什么?你基本上会说,好吧,与其做任何其他事情,你只是对每个位置编码说,将这个位置编码索引除以二。非常简单,对吧?那么对于 2K 窗口,它将映射回 2K;对于 4K 窗口,它将映射回 2K。
所以每个位置编码都变成了前一层、前一版本中位置编码的插值。并使用这种变化后的 Transformer。你只用几百个样本来训练模型,突然间它表现得非常好。原因是我们发现注意力函数实际上表现不佳。
对吧?所以如果你进行插值,它表现得相当好。但如果你进行外推,突然间它会给出超出训练窗口范围的非常糟糕的分数。这就是为什么我们应该进行插值而不是外推的原因。是的,这就是原因。如果我们使用我们的方法,那么我们实际上可以训练能够扩展到长上下文窗口的模型,只需不到 1000 步的微调。
你可以将其扩展到原始上下文窗口长度的八倍。这实际上比如果不改变模型中的任何内容而直接进行硬微调要高效得多。例如,在这种情况下,两百步就足以将窗口从 2K 扩展到 8K、16K 或 32K。
对吧?所以你只需要大约两百步,但如果只是进行微调,那么你确实需要更多的微调。你可能需要大约一千步,但仍然无法真正扩展到 8K 或扩展到 2.5K。所以如果你进行位置编码的插值,效率会高得多。
是的,而且性能并没有真正下降太多。这意味着它在所有基准测试中大致保持不变。是的,正如我所说,论文发布两天后,你在 Reddit 上得到了更好的东西。竞争就是这样激烈。所以我们实际上看到了更多沿着这个方向出来的论文。
我希望人们能从这些见解中受益,这基本上是我上次讲座的全部内容。谢谢你的关注。是的。你所说的语言模型中的插值和外推是什么意思?那是什么意思?是的,我的意思非常简单。例如,你从窗口为 2K 开始。
2K 意味着对于每个令牌,你首先会根据位置分配一个索引。从 0 到 2K 减 1。然后,给定这个索引,你可以计算它们的位置编码。对于这一个,我们使用的是 RoPE。这是人们用于这些模型的方法。
为了计算它,你首先减去这两个位置编码,即位置索引,然后使用这个 n 减 n 的数,你基本上将其代入这个方程中。你可以根据此计算注意力。是的,这就是你如何使用位置来进行位置编码的。
我认为第一个问题是关于如何将理论论文中的见解与例如大语言模型的缩放定律以及涌现能力联系起来。
论文中的理论图景,我的意思是,它们并非完全缺席于早期的模型。你是指在大型模型中如何将两者结合吗?我认为人们已经在使用了,对吧?Siri 是如何解释的呢?你知道,当我们训练大得多的模型时,我们会获得更强的涌现能力。哦,我明白了,我明白了。好的,所以我认为对于 Siri 来说,这肯定是适用的。我的意思是,Siri 实际上是一个深层堆栈。对。所以有一系列主要是经验性的,并试图描述这些现象。我会说像缩放定律以及涌现行为。还有一系列更侧重于总结正在发生的事情。对,所以这个理论肯定非常适用于当前模型,对吧?
例如,根据缩放定律,你可以知道,如果你将模型扩大十倍,将数据扩大十倍,性能会发生什么变化?你基本上会得到一条曲线。这条曲线会告诉你预测将要发生的事情。对,所以这在许多情况下非常有用,对吧?所以,对于像我我们在这里讨论的这种理论,它更多的是从第一性原理出发,对吧?从公式出发,思考公式将实现什么样的后果。对,所以这可能更难应用于实际应用程序。但如果我们做得足够好,那么突然间我们就知道了一切。在这个过程中,可能会有许多不同的适用场景。所以这是一段非常艰难的旅程,但也许在未来它会产生非常强烈的应用。
是的。那么,你认为从第一性原理到缩放定律等事物的最直接下一步是什么?是的,所以我认为对于缩放定律之类的事情,会发生的情况是,给定所有的理论研究,然后基于理论研究,你可能能够模拟如果我拥有更多数据会发生什么。对,所以边界会是什么样子,那将成为你经验观察到的缩放定律,对吧?所以在这种情况下,这可能比目前我们拥有的纯经验性的缩放定律更进一步。是的,这是可能的。
我认为物理学家在许多不同的场景中已经这样做了,对吧?你可以从第一性原理出发,得出一些方程,然后说,如果你有一千个原子,或者像 10 的 32 次方个原子,会发生什么?然后你会得出一种更宏观和经验性的定律,并尝试用真实的实验来拟合它,对吧?所以这可能是一个可能的方向。这个过程确实各不相同。我的意思是,好吧,我会给出个人观点,对吧?所以我从 2017 年开始做一系列研究,那时是一个非常痛苦的过程,我必须说。是的,所以在那个过程中,你可能会花几个月时间在一个不可能证明的问题上。
即使你证明了它,你也看不到任何好处。你意识到你证明的东西毫无意义。你不需要证明那个,对吧?所以起初这个过程实际上非常痛苦。但后来,我的意思是,经过几年的探索之后,人们可能会达到这样一个阶段:你对整体有一个很好的洞察,关于大概的图景,关于系列研究应该如何进行。然后,有了这个粗略的图景,你就知道定理大致应该如何被证明。有些定理,你可以粗略地写下来,即使它们是错误的。那也没关系。这些是像错误的定理,但它们大致是正确的,方向也是对的。然后通过添加约束、添加条件,以及做一些经验性的验证,你可能会更好地知道这应该是什么样子。直到你确定一个既逻辑正确又在经验上有用的论点。对,所以这可能是使理论更加精简的一种方式。
是的,例如在 Drama 论文中,我的意思是,我们提出了这个想法,关于绘制嵌入的核心思想,也许在几天内就完成了。对。所以一旦你推导出那个方程,好的,好的,完成了。你得到了它。然后我们知道,好的,肯定有下一步。然后我们可以在那里做更多工作。所有的工作基本上都对应着那个。对,所以我会说,系列研究基本上不是我的主要推动力。我的意思是,我们还有很多其他工作要做,但是,嗯,但已经有一个很好的开端。嗯,然后你可以推导定理。你可以思考如何获得好的解决方案。嗯,在很短的时间内。是的。所以我认为如果我们经历那个过程,那么你会尝试。你可以同时具备做理论的能力。你也可以做实验。你也做经验性工作。是的,这是一种艺术。是的,我会说你必须先尝试几件事。呃,然后一旦你尝试了,然后你意识到,哦,那可能是不正确的,对吧?
所以然后你转向不同的假设。这基本上是一个在你的符号结构和现实世界结构之间来回往复的过程,对吧?所以你从现实世界出发,得出一些假设,然后来到符号侧。然后观察它并思考我们应该做什么,然后得出好的结论,如果在符号上我们做这些假设,可能会使事情变得更容易。然后在符号上思考,好的,为什么这个符号假设是否有意义,对吧?然后回到实践侧,然后来回往复,直到你收敛到既在符号上有趣又与现实世界相关的假设。然后你就收敛到那里,对吧?随着时间的推移,你会在这方面做得越来越好。
好的,也许第一个显然是 t 趋向于无穷大,对吧?所以那是被采用的一个。我们有合作者,所以第二作者实际上做了许多详细的工作,他首先得出了一种置信界。如果 t 是有限的,我会说好吧,忘掉它,就说 t 趋向于无穷大,因为那基本上会捕捉到图景的感觉,而我们不太关心数学细节,对吧?所以在这种情况下,这似乎是一个好的假设。是的。但是我会,我会,但我永远不会假设你的特征是固定的,对吧?那实际上不是正确的做法。即使
这会让数学变得简单得多,但这基本上会破坏整个物理图像,这不是什么好事,所以总是要保持平衡。如果你有一个好的假设,就去尝试它,但同时要确保这个假设不会破坏你想做的事情。是的,关于这一点,其实我可以讲另一个故事,因为对于分层模型,多年来我一直在尝试在这方面做一些工作。
我的硕士论文就是关于某些视觉模型的分层表示,那是一篇论文,但没人读过。无论如何,这是非常长期的努力。对于卷积神经网络(CNNs),我们也尝试过。如果你查阅一些论文,我必须说,这篇期刊论文是我第一篇被接受的分层分析论文。之前我们尝试做的所有分层分析论文都被拒了,因为符号太复杂。
这非常棘手。对于CNNs,确实存在分层结构,这也是我的动机之一,因为我最初是从事视觉研究的。如果你查阅我的出版物,我最初做的是视觉工作,显然,视觉领域的人对分层表示非常着迷,对吧?所以我们有很多这样的见解。
但我认为CNN和Transformer的区别在于,Transformer使用嵌入(embeddings),而嵌入非常强大,超级强大。你可以这样想:在高维空间中,有一个有趣的性质。在高维空间中,你可以将2的d次方个向量放入这个空间,并保持它们几乎相互正交。
这实际上是一个非常美妙的性质。你基本上可以在这个有限的样本、有限的空间中放入指数级的内容或对象。但如果你做CNN,情况会怎样呢?你本质上是在对概念进行独热(one-hot)表示。
你看,也许这个token代表某物,那个token代表某物,这实际上是独热表示。但如果你进行独热表示,你需要它们相互正交,那么你需要2的d次方维的空间。所以这实际上非常高效。
使事情高效化的另一个要点是,Transformer还可以执行大量的推理任务。我相信,这种推理肯定与嵌入的表示有关。所以我认为,也许“a”可以由多个嵌入向量的求和来表示。
其中一个向量代表一个字母,另一个向量代表首字母,选择单词,比如是小写,类似这样的东西。这种表示非常有用,因为它实际上被解耦为不同的属性,这些属性可以在Transformer的计算中单独计算,这可能是我们接下来想要分析的内容。