Self -Attention、Multi-Head Attention、Cross-Attention
Self -Attention Transformer结构图
上图是论文中 Transformer 的内部结构图,左侧为 Encoder block,右侧为 Decoder block。红色圈中的部分为 Multi-Head Attention,是由多个 Self-Attention组成的,可以看到 Encoder block 包含一个 Multi-Head Attention,而 Decoder block 包含两个 Multi-Head Attention (其中有一个用到 Masked)。Multi-Head Attention 上方还包括一个 Add & Norm 层,Add 表示残差连接 (Residual Connection) 用于防止网络退化,Norm 表示 Layer Normalization,用于对每一层的激活值进行归一化。
Self -Attention是一端的注意力机制,输入相同。
在self-attention中,每个单词有3个不同的向量,它们分别是Query向量(
Q
Q
Q ),Key向量(
K
K
K )和Value向量(
V
V
V ),长度均是64。它们是通过3个不同的权值矩阵由嵌入向量
X
X
X 乘以三个不同的权值矩阵
W
Q
W^Q
WQ,
W
K
W^K
WK ,
W
V
W^V
WV 得到,其中三个矩阵的尺寸也是相同的。均是
512
×
64
512\times64
512×64 。那么Query,Key,Value是什么意思呢?它们在Attention的计算中扮演着什么角色呢?我们先看一下Attention的计算方法,整个过程可以分成7步:
- 将输入单词转化成嵌入向量;
- 根据嵌入向量得到 q q q, k k k , v v v 三个向量;
- 为每个向量计算一个score: s c o r e = q ⋅ k score=q \cdot k score=q⋅k ;
- 为了梯度的稳定,Transformer使用了score归一化,即除以 d k \sqrt {d_k} dk ;
- 对score施以softmax激活函数;
- softmax点乘Value值 v v v ,得到加权的每个输入向量的评分 v v v ;
- 相加之后得到最终的输出结果 z z z: z = Σ v z=\Sigma v z=Σv 。
Query,Key,Value的概念取自于信息检索系统。self-attention中的 Q , K , V Q,K,V Q,K,V也是起着类似的作用,在矩阵计算中,点积是计算两个矩阵相似度的方法之一,因此使用了 Q K T QK^T QKT进行相似度的计算。接着便是根据相似度进行输出的匹配,这里使用了加权匹配的方式,而权值就是query与key的相似度。
Transformer 的输入
Transformer 中单词的输入表示 x由单词 Embedding 和位置 Embedding (Positional Encoding)相加得到。
位置 Embedding
Transformer 中除了单词的 Embedding,还需要使用位置 Embedding 表示单词出现在句子中的位置。因为 Transformer 不采用 RNN 的结构,而是使用全局信息,不能利用单词的顺序信息,而这部分信息对于 NLP 来说非常重要。所以 Transformer 中使用位置 Embedding 保存单词在序列中的相对或绝对位置。
位置 Embedding 用 PE表示,PE 的维度与单词 Embedding 是一样的。PE 可以通过训练得到,也可以使用某种公式计算得到。在 Transformer 中采用了后者,计算公式如下:
其中,pos 表示单词在句子中的位置,d 表示 PE的维度 (与词 Embedding 一样),2i 表示偶数的维度,2i+1 表示奇数维度 (即 2i≤d, 2i+1≤d)。使用这种公式计算 PE 有以下的好处:
- 使 PE 能够适应比训练集里面所有句子更长的句子,假设训练集里面最长的句子是有 20 个单词,突然来了一个长度为 21 的句子,则使用公式计算的方法可以计算出第 21 位的 Embedding。
- 可以让模型容易地计算出相对位置,对于固定长度的间距 k,PE(pos+k) 可以用 PE(pos) 计算得到。因为 Sin(A+B) = Sin(A)Cos(B) + Cos(A)Sin(B), Cos(A+B) = Cos(A)Cos(B) - Sin(A)Sin(B)。
将单词的词 Embedding 和位置 Embedding 相加,就可以得到单词的表示向量 x,x 就是 Transformer 的输入。
Self-Attention 结构
上图是 Self-Attention 的结构,在计算的时候需要用到矩阵Q(查询),K(键值),V(值)。在实际中,Self-Attention 接收的是输入(单词的表示向量x组成的矩阵X) 或者上一个 Encoder block 的输出。而Q,K,V正是通过 Self-Attention 的输入进行线性变换得到的。
Q, K, V 的计算
Self-Attention 的输入用矩阵X进行表示,则可以使用线性变阵矩阵WQ,WK,WV计算得到Q,K,V。计算如下图所示,注意 X, Q, K, V 的每一行都表示一个单词。
公式表式,如下:
Q
=
X
W
q
K
=
X
W
k
V
=
X
W
v
\begin{aligned} Q & =X W_q\\ K & =X W_k\\ V & =X W_v \end{aligned}
QKV=XWq=XWk=XWv
Self-Attention 的输出
得到矩阵 Q, K, V之后就可以计算出 Self-Attention 的输出了,计算的公式如下:
A
t
t
e
n
t
i
o
n
(
Q
,
K
,
V
)
=
s
o
f
t
m
a
x
(
Q
K
T
d
k
)
V
Attention(Q,K,V)=softmax(\frac{QK^T}{\sqrt{d_k}})V
Attention(Q,K,V)=softmax(dkQKT)V
d
k
d_k
dk是
Q
,
K
Q,K
Q,K矩阵的列数,即向量的维度。
公式中计算矩阵Q和K每一行向量的内积,为了防止内积过大,因此除以
d
k
d_k
dk 的平方根。Q乘以K的转置后,得到的矩阵行列数都为 n,n 为句子单词数,这个矩阵可以表示单词之间的 attention 强度。下图为Q乘以
K
T
K^T
KT ,1234 表示的是句子中的单词。
得到
Q
K
T
QK^T
QKT 之后,使用 Softmax 计算每一个单词对于其他单词的 attention 系数,公式中的 Softmax 是对矩阵的每一行进行 Softmax,即每一行的和都变为 1.
得到 Softmax 矩阵之后可以和V相乘,得到最终的输出Z。
上图中 Softmax 矩阵的第 1 行表示单词 1 与其他所有单词的 attention 系数,最终单词 1 的输出
Z
1
Z_1
Z1 等于所有单词 i 的值
V
i
V_i
Vi根据 attention 系数的比例加在一起得到,如下图所示:
Multi-Head Attention
模型在对当前位置的信息进行编码时,会过度的将注意力集中于自身的位置,而可能忽略了其它位置。因此作者采取的一种解决方案就是采用多头注意力机制(MultiHeadAttention)。
Multi-Head Attention相当于
h
h
h个不同的self-attention的集成(ensemble)。在上一步,我们已经知道怎么通过 Self-Attention 计算得到输出矩阵 Z,而 Multi-Head Attention 是由多个 Self-Attention 组合形成的,下图是论文中 Multi-Head Attention 的结构图。
从上图可以看到 Multi-Head Attention 包含多个 Self-Attention 层,首先将输入X分别传递到 h 个不同的 Self-Attention 中,计算得到 h 个输出矩阵Z。下图是 h=8 时候的情况,此时会得到 8 个输出矩阵Z。
公式如下:
Q
=
X
W
q
K
=
X
W
k
V
=
X
W
v
\begin{aligned} Q & =X W_q\\ K & =X W_k\\ V & =X W_v \end{aligned}
QKV=XWq=XWk=XWv
Q
,
K
,
V
∈
R
512
,
W
i
Q
,
W
i
K
,
W
i
V
∈
R
512
×
64
,
W
O
∈
R
512
×
512
,
h
e
a
d
i
∈
R
64
Q,K,V\in R^{512},W_i^Q,W_i^K,W_i^V \in R^{512\times 64},W^O\in R^{512 \times 512},head_i \in R^{64}
Q,K,V∈R512,WiQ,WiK,WiV∈R512×64,WO∈R512×512,headi∈R64
Q
i
=
Q
W
i
Q
,
K
i
=
K
W
i
K
,
V
i
=
V
W
i
V
,
i
=
1
,
…
,
8
h
e
a
d
i
=
A
t
t
e
n
t
i
o
n
(
Q
i
,
K
i
,
V
i
)
,
i
=
1
,
…
,
8
M
u
l
t
i
H
e
a
d
(
Q
,
K
,
V
)
=
C
o
n
c
a
t
(
h
e
a
d
1
,
…
,
h
e
a
d
8
)
\begin{aligned} &Q_i =QW_i^Q,K_i=KW_i^K,V_i=VW_i^V,i=1,\dots,8 \\ &head_i =Attention(Q_i,K_i,V_i),i=1,\dots,8 \\ &MultiHead(Q,K,V)=Concat(head_1,\dots,head_8) \end{aligned}
Qi=QWiQ,Ki=KWiK,Vi=VWiV,i=1,…,8headi=Attention(Qi,Ki,Vi),i=1,…,8MultiHead(Q,K,V)=Concat(head1,…,head8)
意义
对不同位置,不同子空间上进行学习,从而增强模型的表达能力
或者:另一种解释
得到 8 个输出矩阵
Z
1
Z_1
Z1 到
Z
8
Z_8
Z8 之后,Multi-Head Attention 将它们拼接在一起 (Concat),然后传入一个Linear层,得到 Multi-Head Attention 最终的输出Z。
可以看到 Multi-Head Attention 输出的矩阵Z与其输入的矩阵X的维度是一样的。
Encoder 结构
上图红色部分是 Transformer 的 Encoder block 结构,可以看到是由 Multi-Head Attention, Add & Norm, Feed Forward, Add & Norm 组成的。刚刚已经了解了 Multi-Head Attention 的计算过程,现在了解一下 Add & Norm 和 Feed Forward 部分。
Add & Norm
Add & Norm 层由 Add 和 Norm 两部分组成,其计算公式如下:
其中 X表示 Multi-Head Attention 或者 Feed Forward 的输入,MultiHeadAttention(X) 和 FeedForward(X) 表示输出 (输出与输入 X 维度是一样的,所以可以相加)。
Add指 X+MultiHeadAttention(X),是一种残差连接,通常用于解决多层网络训练的问题,可以让网络只关注当前差异的部分,在 ResNet 中经常用到:
Norm指 Layer Normalization,通常用于 RNN 结构,Layer Normalization 会将每一层神经元的输入都转成均值方差都一样的,这样可以加快收敛。
Feed Forward
Feed Forward 层比较简单,是一个两层的全连接层,第一层的激活函数为 Relu,第二层不使用激活函数,对应的公式如下:
max
(
0
,
X
W
1
+
b
1
)
W
2
+
b
2
\max(0,XW_1+b_1)W_2+b_2
max(0,XW1+b1)W2+b2
X是输入,Feed Forward 最终得到的输出矩阵的维度与X一致。
组成 Encoder
通过上面描述的 Multi-Head Attention, Feed Forward, Add & Norm 就可以构造出一个 Encoder block,Encoder block 接收输入矩阵 X ( n × d ) X_{(n\times d)} X(n×d) ,并输出一个矩阵 O n × d O_{n\times d} On×d 。通过多个 Encoder block 叠加就可以组成 Encoder。
第一个 Encoder block 的输入为句子单词的表示向量矩阵,后续 Encoder block 的输入是前一个 Encoder block 的输出,最后一个 Encoder block 输出的矩阵就是编码信息矩阵 C,这一矩阵后续会用到 Decoder 中。
Decoder 结构
上图红色部分为 Transformer 的 Decoder block 结构,与 Encoder block 相似,但是存在一些区别:
- 包含两个 Multi-Head Attention 层。
- 第一个 Multi-Head Attention 层采用了 Masked 操作。
- 第二个 Multi-Head Attention 层的K, V矩阵使用 Encoder 的编码信息矩阵C进行计算,而Q使用上一个 Decoder block 的输出计算。
- 最后有一个 Softmax 层计算下一个翻译单词的概率。
第一个 Multi-Head Attention
Decoder block 的第一个 Multi-Head Attention 采用了 Masked 操作,因为在翻译的过程中是顺序翻译的,即翻译完第 i 个单词,才可以翻译第 i+1 个单词。通过 Masked 操作可以防止第 i 个单词知道 i+1 个单词之后的信息。下面以 “我有一只猫” 翻译成 “I have a cat” 为例,了解一下 Masked 操作。
下面的描述中使用了类似 Teacher Forcing 的概念,在 Decoder 的时候,是需要根据之前的翻译,求解当前最有可能的翻译,如下图所示。首先根据输入 “<Begin>” 预测出第一个单词为 “I”,然后根据输入 “<Begin> I” 预测下一个单词 “have”。
Decoder 可以在训练的过程中使用 Teacher Forcing 并且并行化训练,即将正确的单词序列 (<Begin> I have a cat) 和对应输出 (I have a cat <end>) 传递到 Decoder。那么在预测第 i 个输出时,就要将第 i+1 之后的单词掩盖住,注意 Mask 操作是在 Self-Attention 的 Softmax 之前使用的,下面用 0 1 2 3 4 5 分别表示 “<Begin> I have a cat <end>”。
第一步:是 Decoder 的输入矩阵和 Mask 矩阵,输入矩阵包含 “<Begin> I have a cat” (0, 1, 2, 3, 4) 五个单词的表示向量,Mask 是一个 5×5 的矩阵。在 Mask 可以发现单词 0 只能使用单词 0 的信息,而单词 1 可以使用单词 0, 1 的信息,即只能使用之前的信息。
第二步:接下来的操作和之前的 Self-Attention 一样,通过输入矩阵X计算得到Q,K,V矩阵。然后计算Q和
K
T
K^T
KT的乘积
Q
K
T
QK^T
QKT 。
第三步:在得到
Q
K
T
QK^T
QKT 之后需要进行 Softmax,计算 attention score,我们在 Softmax 之前需要使用Mask矩阵遮挡住每一个单词之后的信息,遮挡操作如下:
得到 Mask
Q
K
T
QK^T
QKT 之后在 Mask
Q
K
T
QK^T
QKT 上进行 Softmax,每一行的和都为 1。但是单词 0 在单词 1, 2, 3, 4 上的 attention score 都为 0。
第四步:使用 Mask
Q
K
T
QK^T
QKT与矩阵 V相乘,得到输出 Z,则单词 1 的输出向量
Z
1
Z_1
Z1 是只包含单词 1 信息的。
第五步:通过上述步骤就可以得到一个 Mask Self-Attention 的输出矩阵
Z
i
Z_i
Zi ,然后和 Encoder 类似,通过 Multi-Head Attention 拼接多个输出
Z
i
Z_i
Zi然后计算得到第一个 Multi-Head Attention 的输出Z,Z与输入X维度一样。
第二个 Multi-Head Attention
Decoder block 第二个 Multi-Head Attention 变化不大, 主要的区别在于其中 Self-Attention 的 K, V矩阵不是使用 上一个 Decoder block 的输出计算的,而是使用 Encoder 的编码信息矩阵 C 计算的。
根据 Encoder 的输出 C计算得到 K, V,根据上一个 Decoder block 的输出 Z 计算 Q (如果是第一个 Decoder block 则使用输入矩阵 X 进行计算),后续的计算方法与之前描述的一致。
这样做的好处是在 Decoder 的时候,每一位单词都可以利用到 Encoder 所有单词的信息 (这些信息无需 Mask)。
Softmax 预测输出单词
Decoder block 最后的部分是利用 Softmax 预测下一个单词,在之前的网络层我们可以得到一个最终的输出 Z,因为 Mask 的存在,使得单词 0 的输出 Z0 只包含单词 0 的信息,如下:
Softmax 根据输出矩阵的每一行预测下一个单词:
这就是 Decoder block 的定义,与 Encoder 一样,Decoder 是由多个 Decoder block 组合而成。
Transformer 总结
Transformer 与 RNN 不同,可以比较好地并行训练。
Transformer 本身是不能利用单词的顺序信息的,因此需要在输入中添加位置 Embedding,否则 Transformer 就是一个词袋模型了。
Transformer 的重点是 Self-Attention 结构,其中用到的 Q, K, V矩阵通过输出进行线性变换得到。
Transformer 中 Multi-Head Attention 中有多个 Self-Attention,可以捕获单词之间多种维度上的相关系数 attention score。
Cross-Attention
Cross-Attention是两端的注意力机制,然后合起来,输入不同。Cross-attention将两个相同维度的嵌入序列不对称地组合在一起,而其中一个序列用作查询Q输入,而另一个序列用作键K和值V输入。
- Transformer架构中混合两种不同嵌入序列的注意力机制
- 两个序列必须具有相同的维度
- 两个序列可以是不同的模式形态(如:文本、声音、图像)
- 一个序列作为输入的Q,定义了输出的序列长度,另一个序列提供输入的K&V
Cross-attention vs Self-attention
Cross-attention的输入来自不同的序列,Self-attention的输入来自同序列,也就是所谓的输入不同,但是除此之外,基本一致。
cross-attention 算法
s o f t m a x ( ( W Q S 2 ) ( W K S 1 ) ) W v S 1 softmax((W_QS_2)(W_KS_1))W_vS_1 softmax((WQS2)(WKS1))WvS1
- 拥有两个序列S1、S2
- 计算S1的K、V
- 计算S2的Q 根据K和Q
- 计算注意力矩阵
- 将V应用于注意力矩阵
- 输出的序列长度与S2一致
Cross-Attention 案例-感知器IO
感知器IO是一个通用的跨域架构,可以处理各种输入和输出,广泛使用交叉注意:
- 将非常长的输入序列(如图像、音频)合并到低维潜在嵌入序列中
- 合并“输出查询”或“命令”来解码输出值,例如我们可以让模型询问一个掩码词
这样做的好处是,通常可以处理很长的序列。层次感知器能够处理更长的序列,将它们分解成子序列,然后合并它们。层次感知器也学习位置编码与一个单独的训练步骤,重建的损失。
示例:
假设有文本数据和图像数据:
1.文本通过一个Transformer编码器处理,输出作为查询向量。
2.图像通过CNN处理,输出经过线性变换生成键和值向量。
3.计算文本查询向量与图像键向量的点积,得到注意力分数。
4.使用这些分数对图像的值向量进行加权,生成最终输出。
交叉注意力可以在多种任务中提升性能,如图像-文本匹配,视觉问答等。
更多推荐
所有评论(0)