有人是这么描述BERT模型的:它的出现,彻底改变了预训练产生词向量和下游具体NLP任务的关系,提出龙骨级的训练词向量概念。不过想了解Bert,也不能着急,要先从tranformer框架聊起。
![a5a959f7f4cf9480ee204fe7f84e4353.png](https://i-blog.csdnimg.cn/blog_migrate/954d286c50bdc2556de1770e741af836.jpeg)
Attention
在学会 Transformer 和 Bert 之前,我们需要理解Attention和Self-Attention机制。Attention的本质是要找到输入的feature的权重分布,这个feature在某一个维度有一个长度的概念,如果我们输入一个长为 n 的 feature,那么 Attention 就要学习一个长为 n 的分布权重,这个权重是由相似度计算出来的,最后返回的得分就将会是权重与feature的加权和。
- Attention的计算过程
Attention的输入是Q,K,V,返回的是一个socre,计算公式如下:
![a59bd07be667c6d86efbf33508dd3413.png](https://i-blog.csdnimg.cn/blog_migrate/73e5672b9e4acc1fe971482a77b5a696.jpeg)
需要注意的是上述公式的下标位置,显然我们需要学习的权重分布是A ,而A和Q、K相关,V就是我们希望去被找到权重的feature。
QKV 英文名字的含义
Q 即为英文中 Query 是指:被查询的序列,可以看到在每次计算相似度的过程中,Q在计算中是一直保持着整体的状态。K 即为英文中 Key 是指:被查询的索引,我们学习到的权重分布A 长度为n,那么A中每一个下标的大小,就代表了对应索引被分配到的权重。所以这个K,控制的是索引。V 即为英文中的 Value 是指:值,也就是我们feature 本身的值,他要去和权重分布做加权和来得到最终的分布。
这里相似度的计算方式有很多种:
![65534b885d3082fc9186b3a0f6cc4411.png](https://i-blog.csdnimg.cn/blog_migrate/f1530dfd734b2441c088754945b8ba44.jpeg)
- HAN中的Attention
我们首先看一下 HAN 的 Attention 中的QKV分别是如何体现的。
在 HAN 中,我们只有一个输入 H,输出为 H和A 的加权平均,所以即H为 Attention 机制中的 Value。我们把H做了一个线性变换变成了U ,然后又随机生成了一个Vm 向量 , 一起计算 A。公式为:
![992cb6bc4601861ed75e85f18530cf0f.png](https://i-blog.csdnimg.cn/blog_migrate/1a5af3225f44ebc056d726c113c253a3.jpeg)
可以看到在公式中Uw一直处于被查询的状态,即一直保持着一个整体的状态,所以我们生成的随机向量即为 Attention 机制中的Query 。而我们做完线性变换生成的U 给 A 生成不同索引的权重值,他即代表我们 Attention 机制中的Key。这里用的相似度公式显然是点积,而在我自己实现的时候遇到了点困难,改成了MLP实现法。
- seq2seq中的Attention
我们来看 seq2seq 中的 Attention 机制,在这个任务中我们需要一步一步的生成Y1,Y2,Y3
,我们会根据每一步生成的Y(实际是一个分布),找到对应的单词。我们的生成公式为:
![727d9b16eaf34df0a88c15ec6bb3c229.png](https://i-blog.csdnimg.cn/blog_migrate/b2812a92ad903c46ef19459337f53f7d.jpeg)
可以看出,每一次生成的时候C都要被更新,而在这个模型中C就是 Attention 模型最终被返回的得分。在 seq2seq模型中,我们把X输入Encoder 生成的值记为 H=[h1,...,hn]我们需要学习关于 H 的权重分布,所以H 即为这里 Value,而这里的 Key 也是 H他自己,他没有像 HAN 中一样做变换,我们每一次要查询的 Query 是已经生成的序列 Y=[y0,y1,y2......],也即为 Decoder 中生成的值 ,显然随着每次生成的变化这个被查询的 Q会变长。这样,由我们的Q,K,V 就能生成出最后的C。
Transformer
Transformer改进了RNN最被人诟病的训练慢的缺点,利用self-attention机制实现快速并行。
- Self-Attention
在 Transformer 中我们要用到的 Attention 方式是 Self-Attention,它与之前的 Attention 有些许的不同。简单的来说,它通过学习三个参数WQ,WK,WV,来对同一个embedding之后的feature 进行转换,将他线性转换成Q、K、V 之后计算出这句话的 Attention 得分。名字中的Self 体现的是所有的Q、K、V 都是由输入自己生成出来的。
归一化:权重分布A在归一化前,要除以输入矩阵的第一维开根号,这会让梯度更稳定。这里也可以使用其它值,8只是默认值,再进行softmax。
返回:这里返回的值和输入的长度维度是一样的,每一个单词对应的输出是所有单词对于当前单词的权重分布与Value得分的加权和。所以他有多少个单词,就做了多少次Attention 得分,这就是self-Attention 。
需要注意的是 Decoder 端的多头 self-attention 需要做mask,因为它在预测时,是“看不到未来的序列的”,所以要将当前预测的单词(token)及其之后的单词(token)全部mask掉。使用多头机制可以理解为CNN中同时使用多个卷积核。
Bert
今天的主角终于粉墨登场,Bert模型的定位是一个预训练模型,同等级的应该是NNLM,Word2vec,Glove,GPT,还有ELMO。
- 预训练模型分类
非语言模型:Word2vec,Glove
语言模型:GPT,NNLM,ELMO,Bert。
其中NNLM是不考虑上下文(单向)的,而ELMO和Bert是考虑上下文(双向)的模型。
- 不同模型的建模
NNLM
其全称为Nerual Network Language Model
目标函数为用前t-1个单词,预测第t个单词,即最大化:
![0005fdb3834ede23e053296bb64c4550.png](https://i-blog.csdnimg.cn/blog_migrate/51e3dc6d05a23a21116d09b4ec348242.jpeg)
ELMO
Elmo的全称为Embedding from Language Models,ELMO是根据上下文单词的语义去动态调整单词的Word Embedding表示,解决了多义词的问题,采用的机制为双层双向LSTM。
ELMO两阶段:第一个阶段是语言模型进行预训练;第二个阶段是在做下游任务时,从预训练网络中提取对应单词的网络各层的Word Embedding作为新特征补充到下游任务中。BERT两阶段过程:第一阶段双向语言模型预训练,第二阶段采用具体任务Fine-tuning。
Bert的优缺点
Bert 对硬件资源的消耗巨大,大模型需要16个tpu,历时四天;更大的模型需要64个tpu,历时四天。Bert 最大的亮点在于效果好及普适性强,几乎所有NLP任务都可以套用Bert这种两阶段解决思路,而且效果应该会有明显提升。
文章部分素材来源:人工智能与算法学习