注意力机制 (Attention):是人工神经网络中一种模仿认知注意力的技术。这种机制可以增强神经网络输入数据中某些部分的权重,同时减弱其他部分的权重,以此将网络的关注点聚焦于数据中最重要的一小部分。数据中哪些部分比其他部分更重要取决于上下文。

本篇文章为论文 Attention Is All You Need 的笔记,因此本文的注意力机制架构遵照原论文。

1 总览

首先,我们通过非常简略的数学方式来总览一下注意力机制的操作过程,感受一下总体框架后,下文再进行详细展开。

对于一段文字:

The quick brown fox jumps over a lazy dog.

首先将其切分为 Token(假设按词切分):

The| quick| brown| fox| jumps| over| a| lazy| dog.

然后通过 Embedding 将单词转为 dmodel 维的词向量:

E1,E2,,E9

然后给词向量乘上 Query 矩阵 WQ,生成每个单词的 dq 维的查询向量 Qi=WQEi

Q1,Q2,,Q9

然后给词向量乘上 Key 矩阵 WK,生成每个单词的 dk 维的键向量 Ki=WKEi

K1,K2,,K9

然后将查询向量和键向量一一做向量点积,得到一个实数,这些值组成一个新的矩阵:

[Q1K1Q2K1Q9K1Q1K2Q2K2Q9K2Q1K9Q2K9Q9K9]

然后对这些值进行 SoftMax 操作:

[Softmax(Q1K1)Softmax(Q2K1)Softmax(Q9K1)Softmax(Q1K2)Softmax(Q2K2)Softmax(Q9K2)Softmax(Q1K9)Softmax(Q2K9)Softmax(Q9K9)]

然后给每一项乘上 Value 矩阵 WV

M=[Softmax(Q1K1)WVSoftmax(Q2K1)WVSoftmax(Q9K1)WVSoftmax(Q1K2)WVSoftmax(Q2K2)WVSoftmax(Q9K2)WVSoftmax(Q1K9)WVSoftmax(Q2K9)WVSoftmax(Q9K9)WV]

然后计算每列的更新值 ΔEi

ΔEi=k=1nMkiEk

原始 Ei 经过注意力机制获取更多信息后,便可以更新为 Ei

Ei=Ei+ΔEi

上述过程的结构可以以下图方式展现:

2 Query 查询

从 Token 嵌入得来的词向量是没有上下文语意信息的,例如 Transformer 到底指变形金刚、变压器还是一种机器学习模型,词向量中是没有相关信息的。为了获取这个 Token 具体的含义,就得从上下文 Token 中获取具体的信息。同时,有些上下文与该 Token 关联不大,比如 The,但有些词语对该 Token 关联非常大,例如 Model. 注意力机制便是让模型自己学会上下文之间的关联程度。

获取上下文关联程度的第一步是是求得查询向量,可以将查询向量理解为该 Token 对上下文提出的“问题”,接下来根据上下文 Token 的”回应“来确认他们之间的关联程度。

对于每个 Token 的词向量 Ei,让它与矩阵 WQ 相乘获得对应的查询向量 Qi=WQEi.

其中,Ei 的维度为 dmodelQi 的维度为 dQ,那么显然 WQ 就是一个 dq×dmodel 的矩阵。需要注意,这个矩阵是学习得来的参数,因此 Query 操作的参数量就是 dq×dmodel.

3 Key 键

Key 向量便是对 Token 提出”问题“的”回应“。

对于每个 Token 的词向量 Ei,让它与矩阵 WK 相乘获得对应的查询向量 Ki=WKEi.

其中,Ei 的维度为 dmodelKi 的维度为 dk,原论文中 dk=dq,那么显然 WK 就是一个 dq×dmodel 的矩阵。需要注意,这个矩阵是学习得来的参数,因此 Key 操作的参数量也是 dq×dmodel.

获得了 Key 值后,就要通过 Compatibility Function (评分函数) 来获得关联程度了。评分函数可以是向量点积:

Compatibility Function(Qi,Ki)=QiKi

上面我们说到原论文中 dk=dq,那么如果 dkdq,那么显然不能靠向量点积的评分函数了,而是需要加性评分函数。加性评分函数使用一个前馈神经网络来计算 Query 向量和 Key 向量的关联程度,这个神经网络只有一个隐藏层。

计算得到关联程度形成矩阵:

[Q1K1Q2K1QiK1Q1K2Q2K2QiK2Q1KiQ2KiQiKi]

接下来有一个可选步骤——Mask (掩码)。对于大语言模型,训练时是通过上文来生成下文,因此上文是不可以从下文获取信息的,否则这就泄露了要预测的信息,造成干扰。但对于文本翻译,就不存在这种问题,因此掩码就是不必要的。

为了防止上文获取下文信息,可以直接将这些关联程度项设为 ,这一步就叫掩码:

[Q1K1Q2K1QiK1Q2K2QiK2QiKi]

还需要注意的一点是,经过点积评分函数后会扩大原数据的方差,导致 Softmax 过于关注小梯度:若 q,k 为独立的随机变量,那么它的均值为 0 方差为 1,但是 qk 的均值为 0,方差为 dk. 为了抵消这个问题,给每一项缩小 dk

[Q1K1dkQ2K1dkQiK1dkQ2K2dkQiK2dkQiKidk]

再进行列 SoftMax,这些被置为 的项就变成 0 了:

M=[Softmax(Q1K1dk)Softmax(Q2K1dk)Softmax(QiK1dk)Softmax(Q2K2dk)Softmax(QiK2dk)0Softmax(QiKidk)]

4 Value 值

计算了关联程度,下一步就是与 Value 矩阵相乘获得最终的更新,记上述矩阵 pq 列元素为 Mpq,那么:

ΔEi=k=1nMkiWVEk

其中,ΔEi 的维度为 dmodelEi 的维度为 dmodel,那么显然 WV 就是一个 dmodel×dmodel 的方阵。需要注意,这个矩阵是学习得来的参数,因此 Value 操作的参数量也是 dmodel×dmodel​.

综上,注意力头总参数量为:dmodel(2dq+dmodel)

上述过程的结构可以以下图方式展现:

用公式来表示就是:

Attention(Q,K,V)=softmax(QKTdk)V

5 多头注意力

实际情况中,dmodel 往往非常大,可以达到 104 数量级,这就导致 WV 这个 dmodel×dmodel 的方阵参数量非常大,占据了模型的大部分参数。

多头注意力的思想就是,与其用一个完整维度的大参数单头注意力,不如将其拆分为多个低维度的小参数注意力,称为多头注意力。这样的效果要好于单头注意力。

我们可以用低秩分解的思想,将 WV 拆分为 dmodel×dvdv×dmodel 的两个矩阵:WVWV. 那么,原来的 Value 计算步骤就变成了:

ΔEi=k=1nMkiWVWVEk

低秩拆分是一种有损压缩技术,可以在一定程度上保留数据的重要特征,但无法完全保留原始数据的所有信息。另外,我们也可以将这个操作理解为做了两次线性映射:先将 Eidmodel 维空间线性映射到低维的 dv 空间,再从低维的 dv 空间重新线性映射回 dmodel 维空间(原论文中,拆分后的 WVWV 就直接被记为 Linear 了).

矩阵乘法可以看作线性映射,例如有一个 n 维向量 p,将它与 m×n 的矩阵 M 相乘可以得到一个 m 维向量 q

Mm×npn×1=qm×1

这个矩阵 M 就实现了将 n 维空间的向量 p 映射到 m 维空间里,变成向量 q​.

上述拆分后仍然是单头注意力,接下来就是叠加注意力头了。最简单想到的一种方式是,直接将单头注意力复制 h 份,每个注意力头有独立的参数(如第 i 个注意力头的参数 WiQ,WiK,WiV,WiV),最后将 h 个注意力头的结果取平均。

但是原论文并没有用这个方式。在原论文中,将单头注意力复制 h 份后,WV 并不是独立的参数,具体来说:

  1. 每个注意力头拥有独立的参数 WiQ,WiK,WiV
  2. 每个注意力头求得 headi=k=1nMkiWVEi,显然这个 headidv 维的向量。
  3. h 个注意力头得到的结果向量拼接得到 MultiHead=Concat(head1,head2,,headN),显然这个 MultiHeadh×dv 维的向量。
  4. 然后将 MultiHeadWV 重新映射回 dmodel 维的空间,显然此时 WV 应当是 dmodel×hdv 的矩阵。

综上,对于 h 个注意力头的多头注意力,参数量为:

hdmodel(dq+dk+dv)+hdmodeldv=hdmodel(dq+dk+2dv)

对于原论文,dq=dk=dv,那么参数量为:4hdmodeldq

上述过程的结构可以以下图方式展现:

需要注意的是,上面原论文的图将 WV 表示为 Linear。虽说看着不一样,实际上是完全一样的,只是符号的区别。
文章目录