目录
一、BERT模型介绍
1.1 BERT简介
1.2 BERT的架构
1.2.1 Embedding模块
1.2.2 双向Transformer模块
1.2.3 预微调模块
1.3 BERT的预训练任务
1.3.1 Masked Language Model (MLM)
1.3.2 Next Sentence Prediction (NSP)
1.4 预训练与微调的关系
1.5 小结
二、BERT模型特点
2.1 BERT模型优缺点
2.2 BERT的MLM任务
2.3 BERT处理长文本的方法
Tips:如何优化 BERT?
三、BERT系列模型介绍
3.1 AlBERT模型
3.1.1 AlBERT模型的架构
3.1.2 AlBERT模型的优化点
3.2 RoBERTa模型
3.2.1 RoBERTa模型的架构
3.2.2 RoBERTa模型的优化点
3.3 MacBert模型
3.3.1 MacBert模型的架构
3.3.2 MacBert模型的优化点
3.4 SpanBERT模型
3.4.1 SpanBERT模型的架构
3.4.2 Span Masking
3.4.3 Span Boundary Objective(SBO)
3.4.4 移除NSP(Next Sentence Prediction)
四、ELMo模型介绍
4.1 ELMo简介
4.2 ELMo架构
4.2.1 总体架构
4.2.2 Embedding模块
4.2.3 两部分的双层LSTM模块
4.2.4 词向量表征模块
4.3 ELMo的预训练任务
4.3.1 ELMo本质思想
4.3.2 ELMo预训练两阶段过程
4.4 ELMo模型的效果
4.5 ELMo的待改进点
4.6 小结
五、GPT模型介绍
5.1 GPT简介
5.2 GPT架构
5.3 GPT训练过程
5.3.1 无监督的预训练语言模型
5.3.2 有监督的下游任务fine-tunning
5.4 小结
六、BERT GPT ELMo模型对比
6.1 BERT、GPT、ELMo之间的不同点
6.2 BERT、GPT、ELMo各自的优点和缺点
6.3 小结
一、BERT模型介绍
1.1 BERT简介
概念
BERT(Bidirectional Encoder Representations from Transformers)是由Google于2018年10月提出的一种基于**Transformer**的预训练语言模型。它在NLP任务中取得了突破性的成果,极大地提升了模型在问答、文本分类等任务上的表现。
BERT在机器阅读理解顶级水平测试SQuAD1.1中表现出惊人的成绩: 全部两个衡量指标上全面超越人类, 并且在11种不同NLP测试中创出SOTA表现。包括将GLUE基准推高至80.4% (绝对改进7.6%), MultiNLI准确度达到86.7% (绝对改进5.6%)。成为NLP发展史上的里程碑式的模型成就。
核心思想
BERT 的核心思想是**双向编码**和**Transformer结构**。 以往的语言模型,如 ELMo,通常采用单向或浅层双向的方式处理文本。BERT 首次使用了真正的双向 Transformer 编码器,使得模型能够同时考虑上下文中的信息,从而更好地理解语言的含义。
1.2 BERT的架构
总体架构: 如下图所示, 最左边的就是BERT的架构图, 可以很清楚的看到BERT采用了Transformer Encoder block进行连接, 因为是一个典型的双向编码模型。
从上面的架构图中可以看到, 宏观上BERT分三个主要模块:
- 最底层黄色标记的Embedding模块
- 中间层蓝色标记的Transformer模块
- 最上层绿色标记的预微调模块
1.2.1 Embedding模块
BERT中的该模块是由三种Embedding共同组成而成, 如下图:
- **Token Embeddings**:词嵌入张量, 第一个单词是CLS标志, 可以用于之后的分类任务
- **Segment Embeddings**:句子分段嵌入张量, 是为了服务后续的两个句子为输入的预训练任务
- **Position Embeddings**:位置编码张量, 此处注意和传统的Transformer不同, 不是三角函数计算的固定位置编码, 而是通过学习得出来的
- 整个Embedding模块的输出张量就是这3个张量的直接加和结果
1.2.2 双向Transformer模块
BERT中只使用了经典Transformer架构中的Encoder部分, 完全舍弃了Decoder部分。而两大预训练任务也集中体现在训练Transformer模块中。
多层 Transformer 编码器, 每个编码器包含:
- **自注意力机制 (Self-Attention):** 这是 Transformer 的核心,允许模型在处理每个单词时,关注句子中其他所有单词,从而捕捉单词之间的关系。 BERT 使用多头自注意力机制 (Multi-Head Attention),可以捕捉不同类型的关系。
- **前馈神经网络 (Feed-Forward Network):** 对自注意力机制的输出进行进一步处理。
- **残差连接 (Residual Connection) 和层归一化 (Layer Normalization):** 为了提高模型的训练效率和稳定性。
BERT 模型的层数和隐藏层维度是可配置的。 常见的 BERT 版本包括 BERT-base (12 层编码器,768 个隐藏单元) 和 BERT-large (24 层编码器,1024 个隐藏单元)。
1.2.3 预微调模块
- 经过中间层Transformer的处理后, BERT的最后一层根据任务的不同需求而做不同的调整即可
- 比如对于sequence-level的分类任务, BERT直接取第一个[CLS] token 的final hidden state, 再加一层全连接层后进行softmax来预测最终的标签
- 对于不同的任务, 微调都集中在预微调模块, 几种重要的NLP微调任务架构图展示如下
- a:句子对任务
- 输入:`[CLS] + 句子1 + [SEP] + 句子2 + [SEP]`
- 输出:`[CLS]`标记的隐藏状态经过一个全连接层,输出分类结果(如是否相似)。
- b:文本分类
- 输入:`[CLS] + 句子 + [SEP]`
- 输出:`[CLS]`标记的隐藏状态经过一个全连接层,输出类别概率。
- c:问答任务 (QA)
- 输入:`[CLS] + 问题 + [SEP] + 段落 + [SEP]`
- 输出:模型预测答案在段落中的起始和结束位置。
- d:命名体识别(NER)
- 输入:`[CLS] + 句子 + [SEP]`
- 输出:每个单词的隐藏状态经过一个分类层,输出实体标签(如人名、地名)。
- 从上图中可以发现, 在面对特定任务时, 只需要对预微调层进行微调, 就可以利用Transformer强大的注意力机制来模拟很多下游任务, 并得到SOTA的结果. (句子对关系判断, 单文本主题分类, 问答任务(QA), 单句贴标签(NER))
- 若干可选的超参数建议如下:
- **Batch size**: 16, 32
- **Learning rate (Adam)**: 5e-5, 3e-5, 2e-5
- **Epochs**: 3, 4
1.3 BERT的预训练任务
BERT包含两个预训练任务:
- 任务一: **Masked Language Model** (MLM:带mask的语言模型训练)
- 任务二: **Next Sentence Prediction** (NSP:下一句话预测任务)
1.3.1 Masked Language Model (MLM)
> MLM是BERT的核心预训练任务,旨在让模型学习双向上下文表示。
关于传统的语言模型训练, 都是采用left-to-right, 或者left-to-right + right-to-left结合的方式, 但这种单向方式或者拼接的方式提取特征的能力有限. 为此BERT提出一个深度双向表达模型(deep bidirectional representation)。 即采用MASK任务来训练模型。
在原始训练文本中, 随机的抽取15%的token作为参与MASK任务的对象
在这些被选中的token中, 数据生成器并不是把它们全部变成[MASK], 而是有下列3种情况:
- 在80%的概率下, 用[MASK]标记替换该token, 比如my dog is hairy -> my dog is [MASK]
- 在10%的概率下, 用一个随机的单词替换token, 比如my dog is hairy -> my dog is apple
- 在10%的概率下, 保持该token不变, 比如my dog is hairy -> my dog is hairy
模型在训练的过程中, 并不知道它将要预测哪些单词? 哪些单词是原始的样子? 哪些单词被遮掩成了[MASK]? 哪些单词被替换成了其他单词? 正是在这样一种高度不确定的情况下, 反倒逼着模型快速学习该token的分布式上下文的语义, 尽最大努力学习原始语言说话的样子。同时因为原始文本中只有15%的token参与了MASK操作, 并不会破坏原语言的表达能力和语言规则。
1.3.2 Next Sentence Prediction (NSP)
> NSP任务旨在让模型理解句子间的关系,适用于需要句子对输入的任务(如问答、自然语言推理)。
在NLP中有一类重要的问题比如:QA(Quention-Answer)问答, NLI(Natural Language Inference)自然语言推理, 需要模型能够很好的理解两个句子之间的关系, 从而需要在模型的训练中引入对应的任务. 在BERT中引入的就是Next Sentence Prediction任务。采用的方式是输入句子对(A, B), 模型来预测句子B是不是句子A的真实的下一句话。
所有参与任务训练的语句都被选中作为句子A.
- 其中50%的B是原始文本中真实跟随A的下一句话. (标记为IsNext, 代表正样本)
- 其中50%的B是原始文本中随机抽取的一句话. (标记为NotNext, 代表负样本)
- 模型预测第二个句子是否是第一个句子的下一句,输出是一个二分类标签(是/否)
在任务二中, BERT模型可以在测试集上取得97%-98%的准确率.
1.4 预训练与微调的关系
- **预训练**:在大规模无标签数据上学习通用的语言表示。
- **微调**:在特定任务的小规模有标签数据上调整模型参数,使其适应具体任务。
BERT的预训练和微调机制使其能够高效地迁移到各种NLP任务中,而无需从头训练模型。
1.5 小结
- 什么是BERT
- BERT是一个基于Transformer Encoder的预训练语言模型.
- BERT在11种NLP测试任务中创出SOAT表现.
- BERT的结构
- 最底层的Embedding模块, 包括Token Embeddings, Segment Embeddings, Position Embeddings.
- 中间层的Transformer模块, 只使用了经典Transformer架构中的Encoder部分.
- 最上层的预微调模块, 具体根据不同的任务类型来做相应的处理.
- BERT的两大预训练任务
- MLM任务(Masked Language Model), 在原始文本中随机抽取15%的token参与任务.
- 在80%概率下, 用[MASK]替换该token.
- 在10%概率下, 用一个随机的单词替换该token.
- 在10%概率下, 保持该token不变.
- NSP任务(Next Sentence Prediction), 采用的方式是输入句子对(A, B), 模型预测句子B是不是句子A的真实的下一句话.
- 其中50%的B是原始文本中真实跟随A的下一句话.(标记为IsNext, 代表正样本)
- 其中50%的B是原始文本中随机抽取的一句话. (标记为NotNext, 代表负样本)
二、BERT模型特点
2.1 BERT模型优缺点
- 优点
- **双向上下文编码:** 这是 BERT 最显著的优势。 它能够同时考虑单词的前后文信息,从而更好地理解单词的含义和句子结构。 这与之前的许多语言模型不同,它们通常只能单向地处理文本。 这种双向性极大地提高了模型的表达能力和准确性。
- **预训练和微调:** BERT 的预训练和微调范式非常高效。 预训练阶段学习通用的语言表示,微调阶段则针对特定下游任务进行适配。 这种方式只需要少量的数据和计算资源即可实现很好的效果,大大降低了开发新模型的成本和时间。
- **强大的性能:** 在许多 NLP 任务中,BERT 都取得了 state-of-the-art 的结果,包括文本分类、问答、命名实体识别、自然语言推理等。 这证明了 BERT 模型的强大性和通用性。
- **可扩展性:** BERT 的架构可以方便地扩展到更大的模型规模,从而进一步提高性能。 例如,BERT-large 版本就比 BERT-base 版本拥有更多的参数和更高的性能。
- **开放源码:** BERT 的代码和预训练模型都是公开的,这方便了研究者和开发者使用和改进 BERT 模型。
- 缺点
- **计算资源消耗大:** BERT 模型的参数量非常大,训练和推理都需要大量的计算资源 (GPU 和内存),这限制了其在资源有限的环境下的应用。预训练尤其需要巨大的计算能力和时间。
- **内存占用高:** BERT 模型的庞大参数量导致其内存占用非常高,这对于一些内存受限的设备来说是一个挑战。
- **可解释性差:** BERT 模型是一个黑盒模型,其内部机制难以理解。 这使得我们难以分析模型的决策过程,也限制了模型的可信度和可解释性。
- **训练数据依赖:** BERT 模型的性能严重依赖于预训练数据的质量和规模。 如果预训练数据存在偏差或噪声,则会影响模型的性能。 此外,特定领域的应用可能需要大量的特定领域数据进行微调。
- **对长文本处理能力有限:** 原始的 BERT 模型对长文本的处理能力有限,因为其自注意力机制的计算复杂度是序列长度的平方。虽然已经有许多改进的模型 (例如 Longformer, Reformer) 解决了这个问题,但仍然是一个需要关注的方面。
- **Next Sentence Prediction (NSP) 任务的有效性:** 后续研究表明 NSP 任务的有效性存疑,甚至可能对某些任务产生负面影响。 许多改进的 BERT 版本已经移除了 NSP 任务。
2.2 BERT的MLM任务
BERT的MLM任务中为什么采用了80%, 10%, 10%的策略?
- 首先, 如果所有参与训练的token被100%的[MASK], 那么在fine-tunning的时候所有单词都是已知的, 不存在[MASK], 那么模型就只能根据其他token的信息和语序结构来预测当前词, 而无法利用到这个词本身的信息, 因为它们从未出现在训练过程中, 等于模型从未接触到它们的信息, 等于整个语义空间损失了部分信息. 采用80%的概率下应用[MASK], 既可以让模型去学着预测这些单词, 又以20%的概率保留了语义信息展示给模型.
- 保留下来的信息如果全部使用原始token, 那么模型在预训练的时候可能会偷懒, 直接照抄当前token信息. 采用10%概率下random token来随机替换当前token, 会让模型不能去死记硬背当前的token, 而去尽力学习单词周边的语义表达和远距离的信息依赖, 尝试建模完整的语言信息.
- 最后再以10%的概率保留原始的token, 意义就是保留语言本来的面貌, 让信息不至于完全被遮掩, 使得模型可以"看清"真实的语言面貌.
2.3 BERT处理长文本的方法
首选要明确一点, BERT预训练模型所接收的最大sequence长度是512.
那么对于长文本(文本长度超过512的句子), 就需要特殊的方式来构造训练样本. 核心就是如何进行截断.
- head-only方式: 这是只保留长文本头部信息的截断方式, 具体为保存前510个token (要留两个位置给[CLS]和[SEP]).
- tail-only方式: 这是只保留长文本尾部信息的截断方式, 具体为保存最后510个token (要留两个位置给[CLS]和[SEP]).
- head+only方式: 选择前128个token和最后382个token (文本总长度在800以内), 或者前256个token和最后254个token (文本总长度大于800).
Tips:如何优化 BERT?
**降低计算量**:
- **DistilBERT**(知识蒸馏):减少 40% 参数,推理速度提升 60%。
- **ALBERT**(参数共享):减少参数量,提高效率。
- **TinyBERT**(剪枝 + 量化):适用于移动端推理。
**优化长文本处理**:
- **Longformer**、**BigBird**:采用稀疏注意力机制,可处理超过512个token的文本。
**结合知识增强**:
- **ERNIE(百度)、LUKE**:融合知识图谱,提高常识推理能力。
三、BERT系列模型介绍
3.1 AlBERT模型
ALBERT(A Lite BERT)是谷歌在 2019 年提出的一种 BERT 的轻量级优化版本,主要目标是减少参数规模,提高训练速度和性能。它通过参数共享、因子化嵌入、去除 NSP 任务等优化手段,在降低计算成本的同时,仍能保持甚至超越 BERT 的性能。
3.1.1 AlBERT模型的架构
-
AlBERT模型发布于ICLR 2020会议, 是基于BERT模型的重要改进版本. 是谷歌研究院和芝加哥大学共同发布的研究成果.
-
论文全称<< A Lite BERT For Self-Supervised Learning Of Language Representations >>.
-
从模型架构上看, AlBERT和BERT基本一致, 核心模块都是基于Transformer的强大特征提取能力.
-
在本篇论文中, 首先对比了过去几年预训练模型的主流操作思路:
-
大规模的语料
-
更深的网络, 更多的参数
-
多任务训练
-
3.1.2 AlBERT模型的优化点
相比较于BERT模型, AlBERT的出发点即是希望降低预训练的难度, 同时提升模型关键能力,主要引入了5大优化:
词嵌入参数的因式分解
隐藏层之间的参数共享
去掉NSP, 增加SOP预训练任务
去掉dropout操作
MLM任务的优化
第一: 词嵌入参数的因式分解
-
AlBERT的作者认为, 词向量只记录了少量的词汇本身的信息, 更多的语义信息和句法信息包含在隐藏层中。因此词嵌入的维度不一定非要和隐藏层的维度一致。
-
ALBERT的优化:
-
将词嵌入维度降低(如 128 维),然后通过 全连接层映射到隐藏层维度(如 768 维)。
-
-
效果:
-
大幅减少参数量,降低计算资源需求,同时保持语义表达能力。
-
-
具体做法就是通过因式分解来降低嵌入矩阵的参数:
-
BERT: embedding_dim * vocab_size = hidden_size * vocab_size, 其中embedding_dim=768, vocab_size大约为30000左右的级别, 大约等于30000 * 768 = 23040000(2300万).
-
AlBERT: vocab_size * project + project * hidden_size, 其中project是因式分解的中间映射层维度, 一般取128, 参数总量大约等于30000 * 128 + 128 * 768 = 3938304(390万).
-
对比:
模型 | 词嵌入维度 | 隐藏层维度 | 嵌入层参数量 |
---|---|---|---|
BERT-Base | 768 | 768 | 23M |
ALBERT-Base | 128 | 768 | 3.9M |
第二: 隐藏层之间的参数共享
-
在BERT模型中, 无论是12层的base, 还是24层的large模型, 其中每一个Encoder Block都拥有独立的参数模块, 包含多头注意力子层, 前馈全连接层. 非常重要的一点是, 这些层之间的参数都是独立的, 随着训练的进行都不一样了!
-
那么为了减少模型的参数量, 一个很直观的做法便是让这些层之间的参数共享, 本质上只有一套Encoder Block的参数!
-
在AlBERT模型中, 所有的多头注意力子层, 全连接层的参数都是分别共享的, 通过这样的方式, AlBERT属于Block的参数量在BERT的基础上, 分别下降到原来的1/12, 1/24.
-
ALBERT的优化:
-
所有 Transformer 层 共享相同的参数(包括 Self-Attention、FFN 层等),极大地减少了参数量。
-
-
效果:
-
大幅降低模型大小,但仍保持深层 Transformer 网络的表达能力。
-
提高训练效率,减少显存占用,使得大规模训练变得更加可行。
-
对比:
模型 | Transformer 层 | 参数量 |
---|---|---|
BERT-Base | 12 层 | 110M |
BERT-Large | 24 层 | 340M |
ALBERT-Base | 12 层 | 12M |
ALBERT-Large | 24 层 | 18M |
第三: 去掉NSP, 增加SOP预训练任务
-
BERT模型的成功很大程度上取决于两点, 一个是基础架构采用Transformer, 另一个就是精心设计的两大预训练任务, MLM和NSP。但是BERT提出后不久, 便有研究人员对NSP任务提出质疑, 我们也可以反思一下NSP任务有什么问题?
-
在AlBERT模型中, 直接舍弃掉了NSP任务, 新提出了SOP任务(Sentence Order Prediction), 即两句话的顺序预测, 文本中正常语序的先后两句话[A, B]作为正样本, 则[B, A]作为负样本.
-
增加了SOP预训练任务后, 使得AlBERT拥有了更强大的语义理解能力和语序关系的预测能力.
-
ALBERT 的优化:
-
使用 SOP(Sentence Order Prediction)任务
:
-
IsNext: 保持原始句子顺序
-
NotNext: 交换句子顺序
-
-
-
效果:
-
SOP 比 NSP 更难,迫使模型学习更深层次的句子关系。
-
提升模型在 QA、文本匹配等任务上的表现。
-
第四: 去掉dropout操作
-
原始论文中提到, 在AlBERT训练达到100万个batch_size时, 模型依然没有过拟合, 作者基于这个试验结果直接去掉了Dropout操作, 竟然意外的发现AlBERT对下游任务的效果有了进一步的提升. 这是NLP领域第一次发现dropout对大规模预训练模型会造成负面影响, 也使得AlBERT v2.0版本成为第一个不使用dropout操作而获得优异表现的主流预训练模型
第五: MLM任务的优化
-
segments-pair的优化:
-
BERT为了加速训练, 前90%的steps使用了长度为128个token的短句子, 后10%的steps才使用长度为512个token的长句子.
-
AlBERT在90%的steps中使用了长度为512个token的长句子, 更长的句子可以提供更多上下文信息, 可以显著提升模型的能力.
-
-
Masked-Ngram-LM的优化:
-
BERT的MLM目标是随机mask掉15%的token来进行预测, 其中的token早已分好, 一个个算.
-
AlBERT预测的是Ngram片段, 每个片段长度为n (n=1,2,3), 每个Ngram片段的概率按照公式分别计算即可. 比如1-gram, 2-gram, 3-gram的概率分别为6/11, 3/11, 2/11.
-
AlBERT系列中包含一个albert-tiny模型, 隐藏层仅有4层, 参数量1.8M, 非常轻巧. 相比较BERT, 其训练和推理速度提升约10倍, 但精度基本保留, 语义相似度数据集LCQMC测试集达到85.4%, 相比于bert-base仅下降1.5%, 非常优秀.
3.2 RoBERTa模型
RoBERTa(Robustly Optimized BERT Approach) 由 Facebook AI 在 2019 年提出,主要目的是优化 BERT 的训练策略,使其在各种 NLP 任务(如 GLUE、RACE、SQuAD)上取得更好的性能。
与 ALBERT 主要聚焦于减少参数量不同,RoBERTa 主要通过更好的预训练策略来提高 BERT 的性能,而无需改变模型架构。
3.2.1 RoBERTa模型的架构
-
原始论文<< RoBERTa: A Robustly Optimized BERT Pretraining Approach >>, 由FaceBook和华盛顿大学联合于2019年提出的模型.
-
从模型架构上看, RoBERTa和BERT完全一致, 核心模块都是基于Transformer的强大特征提取能力. 改进点主要集中在一些训练细节上.
-
第1点: More data
-
第2点: Larger batch size
-
第3点: Training longer
-
第4点: No NSP
-
第5点: Dynamic masking
-
第6点: Byte level BPE
-
3.2.2 RoBERTa模型的优化点
针对于上面提到的6点细节, 一一展开说明:
第一: More data (更大的数据量)
-
原始BERT的训练语料采用了16GB的文本数据.
-
RoBERTa采用了160GB的文本数据.
-
Books Corpus + English Wikipedia (16GB): BERT原文使用的之数据.
-
CC-News (76GB): 自CommonCrawl News数据中筛选后得到数据, 约含6300万篇新闻, 2016年9月-2019年2月.
-
OpenWebText (38GB): 该数据是借鉴GPT2, 从Reddit论坛中获取, 取点赞数大于3的内容.
-
Storie (31GB): 同样从CommonCrawl获取, 属于故事类数据, 而非新闻类.
-
第二: Larger batch size (更大的batch size)
-
BERT采用的batch size等于256.
-
RoBERTa的训练在多种模式下采用了更大的batch size, 从256一直到最大的8000.
-
使用更大的批量大小进行训练,这有助于模型收敛到更好的局部最小值。 实验表明,更大的批量大小可以提高模型的泛化能力.
第三: Training longer (更多的训练步数)
-
RoBERTa的训练采用了更多的训练步数, 让模型充分学习数据中的特征.
第四: No NSP (去掉NSP任务)
-
从2019年开始, 已经有越来越多的证据表明NSP任务对于大型预训练模型是一个负面作用, 因此在RoBERTa中直接取消掉NSP任务.
-
论文作者进行了多组对照试验:
-
Segment + NSP (即BERT模式). 输入包含两部分, 每个部分是来自同一文档或者不同文档的segment(segment是连续的多个句子), 这两个segment的token总数少于512, 预训练包含MLM任务和NSP任务.
-
Sentence pair + NSP (使用两个连续的句子 + NSP, 并采用更大的batch size). 输入也是包含两部分, 每个部分是来自同一个文档或者不同文档的单个句子, 这两个句子的token 总数少于512. 由于这些输入明显少于512个tokens, 因此增加batch size的大小, 以使tokens总数保持与SEGMENT-PAIR + NSP相似, 预训练包含MLM任务和NSP任务.
-
Full-sentences (如果输入的最大长度为512, 那么尽量选择512长度的连续句子; 如果跨越document, 就在中间加上一个特殊分隔符, 比如[SEP]; 该试验没有NSP). 输入只有一部分(而不是两部分), 来自同一个文档或者不同文档的连续多个句子, token总数不超过512. 输入可能跨越文档边界, 如果跨文档, 则在上一个文档末尾添加文档边界token, 预训练不包含NSP任务.
-
Document-sentences (和情况3一样, 但是步跨越document; 该实验没有NSP). 输入只有一部分(而不是两部分), 输入的构造类似于Full-sentences, 只是不需要跨越文档边界, 其输入来自同一个文档的连续句子, token总数不超过512. 在文档末尾附近采样的输入可以短于512个tokens, 因此在这些情况下动态增加batch size大小以达到与Full-sentecens相同的tokens总数, 预训练不包含NSP任务.
-
-
总的来说, 实验结果表明1 < 2 < 3 < 4.
-
真实句子过短的话, 不如拼接成句子段.
-
没有NSP任务更优.
-
不跨越document更优.
-
第五: Dynamic masking (采用动态masking策略)
-
原始静态mask: 即BERT版本的mask策略, 准备训练数据时, 每个样本只会进行一次随机mask(因此每个epoch都是重复的), 后续的每个训练步都采用相同的mask方式, 这是原始静态mask.
-
动态mask: 并没有在预处理的时候执行mask, 而是在每次向模型提供输入时动态生成mask, 所以到底哪些tokens被mask掉了是时刻变化的, 无法提前预知的.
第六: Byte level BPE (采用字节级别的Encoding)
-
基于char-level: 原始BERT的方式, 在中文场景下就是处理一个个的汉字.
-
基于bytes-level: 与char-level的区别在于编码的粒度是bytes, 而不是unicode字符作为sub-word的基本单位.
-
当采用bytes-level的BPE之后, 词表大小从3万(原始BERT的char-level)增加到5万. 这分别为BERT-base和BERT-large增加了1500万和2000万额外的参数. 之前有研究表明, 这样的做法在有些下游任务上会导致轻微的性能下降. 但论文作者相信: 这种统一编码的优势会超过性能的轻微下降.
3.3 MacBert模型
MacBERT(MLM as correction BERT)是BERT的一个改进版本,由哈工大NLP实验室在2020年提出。MacBERT通过改进BERT的预训练任务和训练策略,进一步提升了模型在中文自然语言处理任务中的性能。
3.3.1 MacBert模型的架构
-
MacBert模型由哈工大NLP实验室于2020年11月提出, 2021年5月发布应用, 是针对于BERT模型做了优化改良后的预训练模型.
-
<< Revisiting Pre-trained Models for Chinese Natural Language Processing >>, 通过原始论文题目也可以知道, MacBert是针对于中文场景下的BERT优化.
-
MacBert模型的架构和BERT大部分保持一致, 最大的变化有两点:
-
对于MLM预训练任务, 采用了不同的MASK策略.
-
删除了NSP任务, 替换成SOP任务.
-
3.3.2 MacBert模型的优化点
第一: 对于MLM预训练任务, 采用了不同的MASK策略
-
使用了全词masked以及n-gram masked策略来选择tokens如何被遮掩, 从单个字符到4个字符的遮掩比例分别为40%, 30%, 20%, 10%
-
原始BERT模型中的[MASK]出现在训练阶段, 但没有出现在微调阶段, 这会造成语义偏移(exposure bias)的问题. 因此在MacBert中提出使用类似的单词来进行masked. 具体来说, 使用基于Word2Vec相似度计算包训练词向量, 后续利用这里面找近义词的功能来辅助mask, 比如以30%的概率选择了一个3-gram的单词进行masked, 则将在Word2Vec中寻找3-gram的近义词来替换, 在极少数情况下, 当没有符合条件的相似单词时, 策略会进行降级, 直接使用随机单词进行替换.
-
使用15%的百分比对输入单词进行MASK, 其中80%的概率下执行策略2(即替换为相似单词), 10%的概率下替换为随机单词, 10%的概率下保留原始单词不变.
第二: 删除了NSP任务, 替换成SOP任务
-
第二点优化是直接借鉴了AlBERT模型中提出的SOP任务.
在NLP著名的难任务阅读理解中, MacBert展现出非常优秀的表现。
3.4 SpanBERT模型
SpanBERT 是由Facebook AI Research在2019年提出的一种改进的BERT模型,专门针对跨度(span)级别的任务(如问答、命名实体识别等)进行了优化。SpanBERT通过引入跨度掩码(Span Masking)和跨度边界目标(Span Boundary Objective, SBO)等创新,显著提升了模型在处理跨度相关任务时的性能。
3.4.1 SpanBERT模型的架构
论文的主要贡献有3点:
-
提出了更好的跨度掩码(Span Masking)方案, 再次展示了随机遮掩连续一段tokens比随机遮掩单个token要好.
-
通过加入了跨度边界目标(Span Boundary Objective,SBO)训练任务, 即通过跨度的边界单词来预测被掩盖的跨度内容,增强了BERT的性能, 特别在一些和Span适配的任务, 如抽取式问答.
-
用实验数据获得了和XLNet一致的结果, 发现去除掉NSP任务, 直接用连续一长句训练效果更好.
SpanBERT的架构图如下:
架构图中可以清晰的展示论文的核心贡献点:
-
Span Masking:随机选择连续的多个单词(跨度)进行掩码,而不是随机掩盖单个单词。
-
随机选择一个跨度的起始位置和长度
-
对该跨度内的所有单词进行掩码
-
-
Span Boundary Objective:通过跨度的边界单词来预测被掩盖的跨度内容。
-
使用被掩盖跨度的左右边界单词的表示(通过Transformer编码器得到)
-
将边界单词的表示输入到一个前馈神经网络中,预测被掩盖的跨度内容
-
3.4.2 Span Masking
关于创新的MASK机制, 一般来说都是相对于原始BERT的基准进行改进。对于BERT, 训练时会随机选取整句中的最小输入单元token来进行遮掩, 中文场景下本质上就是进行字级别的MASK。但是这种方式会让本来应该有强相关的一些连在一起的字词, 在训练时被割裂开了。
那么首先想到的做法: 既然能遮掩字, 那么能不能直接遮掩整个词呢? 这就是BERT-WWM模型的思想。
原始输入: 使用语言模型来预测下一个词的概率. 原始BERT: 使用语言[MASK]型来[MASK]测下一个词的[MASK]率. 原句:The quick brown fox jumps over the lazy dog. BERT Mask:The quick brown [MASK] jumps over the lazy dog. 这里,BERT 只 Mask 了 单个 token,无法学到 “brown fox” 这个短语的整体信息。 BERT-WWM: 使用语言[MASK][MASK]来[MASK][MASK]下一个词的[MASK][MASK]. 原句:The quick brown fox jumps over the lazy dog. SpanBERT Mask:The quick [MASK] jumps over the lazy dog. 这里,“brown fox” 这个短语被整体 Mask,让模型学习短语级别的表示。
引申: 百度著名的ERNIE模型中, 直接引入命名实体(Named Entity)的外部知识, 进行整个实体的遮掩, 进行训练。
综合上面所说, 会更自然的想到, 既然整词的MASK, 那么如果拥有词的边界信息会不会让模型的能力更上一层楼呢? SpanBERT给出的是肯定的回答!!!
论文中关于span的选择, 走了这样一个流程:
-
第一步: 根据几何分布(确保短的Span比长的Span更常见), 先随机选择一个span长度
-
第二步: 再根据均匀分布随机选择这一段的起始位置
-
第三步: 最后根据前两步的start和length直接进行MASK
结论: 论文中详细论证了按照上述算法进行MASK, 随机被遮掩的文本平均长度等于3.8
优势:
-
提高 命名实体识别(NER) 和 关系抽取(RE) 的效果,因为这些任务通常依赖于短语级别的表示。
-
使模型能更好地理解句子中的成分结构。
3.4.3 Span Boundary Objective(SBO)
SBO任务是本篇论文最核心的创新点, 希望通过增加这个预训练任务, 可以让被遮掩的Span Boundary的词向量, 能够学习到Span内部的信息。
具体的做法: 在训练时取Span前后边界的两个词, 需要注意这两个词不在Span内, 然后用这两个词向量加上Span中被MASK掉的词的位置向量, 来预测原词。
更详细的操作如下, 即将词向量和位置向量进行拼接, 经过GeLU激活和LayerNorm处理, 连续经过两个全连接层, 得到最终的输出张量
最后预测Span中原词的时候会得到一个损失, 这就是SBO任务的损失; 再将其和BERT自身的MLM任务的损失进行加和, 共同作为SpanBERT的目标损失函数进行训练
3.4.4 移除NSP(Next Sentence Prediction)
单句训练:即从文档中随机抽取连续的多个句子作为一个训练样本
为什么选择Single Sentence(单句训练)而不是BERT的Two Sentence?
-
Single Sentence:训练文本的长度更大, 可以学会长程依赖,能够更好地利用长文本的上下文信息
-
Two Sentence:NSP任务的负例是从其他文档中随机选择的句子,这些句子与正例之间的差异可能过大,导致模型学习到不合理的模式。NSP任务与MLM任务的目标不完全一致,可能导致模型在预训练过程中产生冲突。
-
AlBERT模型已经给出了论证, 因为NSP任务太简单了
移除NSP任务对模型性能和训练效率产生了显著影响,具体包括:
-
性能提升
-
下游任务表现:在RoBERTa、SpanBERT等模型中,移除NSP任务后,模型在多个下游任务(如文本分类、问答、自然语言推理)上的性能有所提升。
-
跨度任务表现:在SpanBERT中,移除NSP任务并结合跨度掩码(Span Masking)和跨度边界目标(SBO),显著提升了模型在跨度级别任务(如问答、指代消解)中的表现。
-
-
训练效率提高
-
简化预训练任务:移除NSP任务后,预训练任务仅包含MLM任务(或MLM任务的变体,如MAC、SBO等),简化了预训练过程。
-
减少计算开销:NSP任务需要构造句子对并进行二分类预测,移除NSP任务后,减少了计算开销。
-
-
模型设计更灵活
-
单句训练:移除NSP任务后,模型可以使用单句进行训练,从而更好地利用长文本的上下文信息。
-
任务特定优化:移除NSP任务后,模型可以更专注于任务特定的优化(如跨度掩码、跨度边界目标等)。
-
四、ELMo模型介绍
4.1 ELMo简介
ELMo(Embeddings from Language Models)是由 **Allen Institute for AI(AI2)** 于 2018 年提出的一种基于 **双向 LSTM** 的 **上下文感知(Contextualized)词向量表示模型**。相比于传统的静态词向量(如 Word2Vec、GloVe),ELMo **动态地为同一个词生成不同的表示**,从而更好地捕捉**语境信息**。
ELMo模型的提出源于论文<< Deep Contextualized Word Representations >>(https://arxiv.org/abs/1802.05365)
ELMo模型提出的动机源于研究人员认为一个好的预训练语言模型应该能够包含丰富的句法和语义信息, 并且能够对多义词进行建模. 而传统的词向量(2013年的word2vec, 2014年的GloVe)都是上下文无关的, 也就是固定的词向量。最典型的例子就是"apple"在不同的语境下, 应该可以表示水果或公司, 但是固定的词向量显然无法做到这一点。因此研究团队利用新的语言模型训练一个上下文相关的预训练模型, 成为ELMo, 并在6个NLP任务上获得提升。
**ELMo 主要特点:**
- **基于双向 LSTM(BiLSTM)** 进行语言建模(不像 BERT 基于 Transformer)。
- **上下文相关(Contextualized)**,相同单词在不同句子中的表示不同。
- **适用于迁移学习(Transfer Learning)**,可用于不同 NLP 任务,如命名实体识别(NER)、文本分类、问答等。
4.2 ELMo架构
4.2.1 总体架构
从上面的架构图中可以看到, 宏观上ELMo分三个主要模块:
- 最底层黄色标记的Embedding模块
- 中间层蓝色标记的两部分双层LSTM模块
- 最上层绿色标记的词向量表征模块
4.2.2 Embedding模块
ELMo最底层的词嵌入采用CNN对字符级进行编码,本质就是获得一个静态的词嵌入向量作为网络的底层输入。
- 输入:句子中的每个单词
- 预训练的 **字符级 CNN(Char-CNN)** 生成初始词表示,而不是使用固定的词向量(如Word2Vec)
- 优点:解决 **OOV(Out of Vocabulary)** 问题,即对于未见过的单词,也能生成合理的表示
4.2.3 两部分的双层LSTM模块
ELMo的架构基于双向语言模型(BiLM),包括前向和后向两个单向语言模型。
这是整个ELMo中最重要的部分, 架构中分成左侧的前向LSTM网络, 和右侧的反向LSTM网络。
ELMo的做法是我们只预训练一个Language Model, 而word embedding是通过输入的句子实时给出的, 这样单词的嵌入向量就包含了上下文的信息, 也就彻底改变了Word2Vec和GloVe的静态词向量的做法。
- ELMo的这一模块分为左右两部分,本质上就是一个双向LM。对于左半部分,给定了N个tokens(t1, t2, ..., tN), Language Model通过前面k-1个位置的token序列来计算第k个token出现的概率(根据前文预测下一个单词),构成前向双层LSTM模型。
$$p(t_1,t_2,\cdots,t_N)=\prod_{k=1}^{N}p(t_k|t_1,t_2,\cdots,t_{k-1})$$
- 同理,对于架构中的右半部分,给定了N个tokens(t(k+1), t(k+2), ..., t(N)),Language Model通过后面N-k个位置的token序列来计算第k个token出现的概率(根据后文预测前一个单词),构成后向双层LSTM模型。
$$p(t_1,t_2,\cdots,t_N)=\prod_{k=1}^{N}p(t_k|t_{k+1},t_{k+2},\cdots,t_{N})$$
- ELMo在训练过程中的目标函数就是最大化下面的公式:
$$\sum_{k=1}^{N}(\log p(t_k|t_1,\cdots,t_{k-1};\Theta_x,\overset{\to}\Theta_{LSTM},\Theta_s)+\log p(t_k|t_{k+1},\cdots,t_{N};\Theta_x,\overset{\leftarrow}\Theta_{LSTM},\Theta_s))$$
其中:
- $$Θ_x$$ 是词嵌入参数
- $$\overset{\to}\Theta_{LSTM}$$ 和 $$\overset{\leftarrow}\Theta_{LSTM}$$ 分别是前向和后向LSTM的参数
- $$Θ_s$$ 是Softmax层的参数
4.2.4 词向量表征模块
因为ELMo是个语言模型, 对于每个token, 通过一个L层的双向LSTM网络可以计算出2L+1个表示向量如下:
$$
R_k = \left\{x_k^{LM}, \overset{\to LM}{h_{k,j}}, \overset{\leftarrow LM}{h_{k,j}} |j=1,\cdots,L\right\}=\left\{ h_{k,j}^{LM}|j=0,\cdots,L\right\}
$$
从上面的公式可以清楚的看到, 有3个不同的组成部分, 第一个就是对token直接进行CNN编码的结果, 也是ELMo最底层模块的输出; 第二个就是前向LSTM的输出结果, 每一层都会有一个输出, 总共L层就会有L个输出; 第三个就是后向LSTM的输出结果, 每一层都会有一个输出, 总共L层就会有L个输出; 综合三部分的输出加在一起, 就是2L+1个输出向量。
通过整个网络, 每一个token得到了2L+1个表示向量, 但是我们希望每一个token能对应一个向量。最简单的做法就是取最上层的输出结果作为token的表示向量, 更通用的做法是加入若干参数来融合所有层的信息, 如下所示:
$$
ELMo_k^{task}=E(R_k;\Theta^{task})=\gamma^{task}\sum_{j=0}^{L}s_j^{task}h_{k,j}^{LM}
$$
其中:
- $$h_{k,j}^{LM}$$ 是第 $$j$$ 层LSTM的输出。
- $$s_j^{task}$$ 是层权重。
- $$\gamma^{task}$$ 是缩放因子。
上式的意思是对于2L+1个向量, 每一个前面都加上一个权重稀疏, 然后直接融合成一个向量, 最后再乘一个系数作为最终该token的词向量。
原始论文中提到最前面的那个系数, 在不同任务中取不同的值效果会有较大的差异, 需要注意在SQuAD中设置为0.01取得的效果要好于设置为1。
原始论文中在进行底层token编码时, 用CNN形成了一个512维的列向量, 也就是初始嵌入维度等于512。中间层使用了双层的LSTM分别进行前向编码和后向编码, 每层的单个LSTM输入维度是512, 输出维度也是512, 保持一致。因为是双向编码并且分左右两部分, 所以每层的输出维度是512*2=1024, 最后进行权重融合后的向量维度就是1024。
4.3 ELMo的预训练任务
4.3.1 ELMo本质思想
ELMo 的关键在于它能够根据上下文生成词向量。它使用一个两层双向 LSTM 网络对文本进行编码,并在每一层产生不同的词向量表示。 这些表示捕捉了不同粒度的语言信息:
- **底层表示:** 捕捉词的语法信息。
- **高层表示:** 捕捉词的语义信息。
通过结合不同层的表示,ELMo 可以获得更丰富的、上下文相关的词向量。它不是简单地用一个静态的词向量来表示一个词,而是根据上下文动态地生成词向量。
**结论:**ELMo模型是根据当前上下文对word embedding动态调整。
4.3.2 ELMo预训练两阶段过程
- **第一阶段:利用语言模型进行预训练**
> 再次回到ELMo的总体架构图, 网络结构采用了双层双向LSTM
- 目前语言模型训练的任务目标是根据单词Wi的上下文去正确预测单词Wi,Wi之前的单词序列context-before称为上文,Wi之后的单词序列context-after称为下文。
- 架构图上左侧的前向双层LSTM代表正方向编码器,输入的是从左向右顺序的除了预测单词Wi之外的上文context-before;右侧的反向双层LSTM代表反方向编码器,输入的是从右向左的逆序的下文context-after。
- 每个编码器的深度都是L=2, 即双层LSTM叠加。
- 使用上述的网络结构利用大量语料做语言模型任务就能预训练好这个网络。当输入一个新句子S_new时,句子中每个单词都能得到对应的3个embedding向量:1-最底层的单词的word embedding;2-中间第一层双向LSTM中对应单词位置的embedding,这层编码对应单词的句法信息更多一些;3-中间第二层双向LSTM中对应单词位置的embedding, 这层编码对应单词的语义信息更多一些。
- ELMo的预训练过程不仅仅学会了单词的word embedding,还学习了一个双层双向的LSTM网络,这两者后续都会用到,是整个ELMo预训练的两大产出结果。
- **第二阶段:在做下游任务时,从预训练网络中提取对应单词的网络各层的word embedding作为新特征补充到下游任务中**
> 比如我们的下游任务是QA问题
- 对于问句X,可以先将句子X作为预训练好的ELMo网络的输入,这样X中每个单词在ELMo中都能获得3个对应的embedding向量。之后赋给这3个向量各自一个权重a,这个权重a既可以是学习得来的也可以是最简单的平均分布赋值,然后把3个向量加权求和,整个成一个词向量。最后将整合后的词向量作为X在自己任务的那个网络结构中对应单词的输入,以此作为新特征补充进下游任务中。对于回答Y可以同样处理。
- 因为ELMo给下游提供的是每个单词的特征形式,所以这一类预训练方法被称为"Feature-based Pre-Training"。
4.4 ELMo模型的效果
ELMo对于多义词问题的解决结果:
- 前面提到静态的word embedding无法解决多义词的问题, 那么ELMo引入上下文动态语义调整后的embedding word可以解决多义词问题吗? 答案正如上图所示, 而且比我们期待的解决效果要更好。
- 上图中的例子, 对于GloVe训练出来的word embedding来说, 多义词比如play, 根据它的embedding找出最接近其语义的单词, 发现结果集合几乎全部都在体育领域, 这很明显是因为训练数据中包含play的语句中体育领域的数量明显占多数导致的。
- 再来看使用ELMo后的效果, 根据上下文动态调整后的embedding word不仅仅能找出对应于"play":"演出"的相同语义的句子, 而且还可以保证找出的句子中的play对应的词性也是相同的, 这真的是超出期待之外的惊喜!
- 原始论文中提到ELMo的试验效果, 在6个NLP主流任务中性能都有不同幅度的提升, 最高的提升达到25%, 任务的覆盖范围很广, 包含句子语义关系判断, 分类任务, 阅读理解等等。
4.5 ELMo的待改进点
ELMo在传统静态word embedding方法(Word2Vec、GloVe)的基础上提升了很多,但是依然存在缺陷,有很大的改进余地:
- 一个很明显的缺点在于特征提取器的选择上, ELMo使用了双向双层LSTM, 而不是现在横扫千军的Transformer, 在特征提取能力上肯定是要弱一些的. 设想如果ELMo的提升提取器选用Transformer, 那么后来的BERT的反响将远不如当时那么火爆了。
- ELMo选用双向拼接的方式进行特征融合, 这种方法肯定不如BERT一体化的双向提取特征好。
4.6 小结
- 什么是ELMo
- ELMo是2018年3月由Allen Institute for AI(AI2)提出的一种基于**双向LSTM**的**上下文感知(Contextualized)词向量表示模型**
- ELMo在6种NLP测试任务中有很大的提升表现
- ELMo的结构
- ELMo架构总体上采用了双向双层LSTM的结构
- 最底层的Embedding模块
- 中间层的双向双层LSTM模块
- 最上层的特征融合模块
- ELMo的预训练任务
- ELMo的本质思想就是根据当前上下文对word embedding进行动态调整的语言模型
- ELMo的预训练是一个明显的两阶段过程.
- 第一阶段: 利用语言模型进行预训练, 得到基础静态词向量和双向双层LSTM网络
- 第二阶段: 在拥有上下文的环境中, 将上下文输入双向双层LSTM中, 得到动态调整后的word embedding, 等于将单词融合进了上下文的语义, 可以更准确的表达单词的真实含义
- ELMo的效果
- 经过与GloVe静态词向量的对比, 明显可以看出ELMo的词向量可以更好的表达真实语义, 更好的解决多义词的问题
- ELMo的待改进点
- ELMo的特征提取器没有选用更强大的Transformer, 在提取特征上肯定弱于现在的最优结果
五、GPT模型介绍
5.1 GPT简介
GPT(Generative Pre-trained Transformer)是 OpenAI 提出的 基于 Transformer 的自回归(Autoregressive)生成模型。它采用 无监督预训练 + 有监督微调 的方式,适用于 自然语言理解(NLU) 和 自然语言生成(NLG) 任务。
OpenAI GPT模型是在Google BERT模型之前提出的, 与BERT最大的区别在于GPT采用了传统的语言模型方法进行预训练, 即使用单词的上文来预测单词, 而BERT是采用了双向上下文的信息共同来预测单词。正是因为训练方法上的区别, 使得GPT更擅长处理自然语言生成任务(NLG), 而BERT更擅长处理自然语言理解任务(NLU)。
GPT发展经历了多个版本的优化:
版本 | 发布时间 | 参数规模 | 优化点 |
---|---|---|---|
GPT-1 | 2018 | 1.17亿 | 采用 标准 Transformer 解码器 结构,使用 BookCorpus 进行预训练。 |
GPT-2 | 2019 | 15亿-175亿 | 引入更大规模数据(WebText),优化 文本生成质量,但无微调机制。 |
GPT-3 | 2020 | 1750亿 | Few-shot / Zero-shot / One-shot 能力增强,支持 多任务泛化。 |
GPT-4 | 2023 | 规模未知 | 增强推理能力,引入多模态(文本 + 图像),更长上下文窗口。 |
5.2 GPT架构
GPT主要基于 Transformer 解码器(Decoder-only),整体架构如下:
GPT由词嵌入(Embedding)、多层Transformer解码器、输出层 组成:
1️⃣ 输入嵌入(Token Embeddings):
使用 Byte-Pair Encoding(BPE) 进行子词分词,将文本转换为 token。
通过 词嵌入矩阵 将 token 映射为固定维度的向量。
2️⃣ 位置编码(Positional Encoding):
GPT 使用 可训练的位置嵌入(Learnable Positional Embeddings),不像 BERT 采用固定三角函数编码。
3️⃣ 多层 Transformer 解码器(Multi-layer Decoder):
由多个 自注意力(Self-Attention)、前馈神经网络(FFN)、残差连接(Residual Connections) 组成。
Masked Self-Attention 机制,确保每个 token 只能看到 之前的 token,防止未来信息泄露。
4️⃣ 输出层(Output Layer):
经过线性变换 + Softmax计算概率分布,生成下一个token。
看三个语言模型的对比架构图, 中间的就是GPT:
从上图可以很清楚的看到GPT采用的是单向Transformer模型, 例如给定一个句子[u1, u2, ..., un], GPT在预测单词ui的时候只会利用[u1, u2, ..., u(i-1)]的信息, 而BERT会同时利用上下文的信息[u1, u2, ..., u(i-1), u(i+1), ..., un]。
作为两大模型的直接对比, BERT采用了Transformer的Encoder模块, 而GPT采用了Transformer的Decoder模块。并且GPT的Decoder Block和经典Transformer Decoder Block还有所不同, 如下图所示:
如上图所示, 经典的Transformer Decoder Block包含3个子层, 分别是Masked Multi-Head Attention层, encoder-decoder attention层, 以及Feed Forward层。但是在GPT中取消了第二个encoder-decoder attention子层, 只保留Masked Multi-Head Attention层, 和Feed Forward层。
作为单向Transformer Decoder模型, GPT利用句子序列信息预测下一个单词的时候, 要使用Masked Multi-Head Attention对单词的下文进行遮掩(look ahead mask), 来防止未来信息的提前泄露。例如给定一个句子包含4个单词[A, B, C, D], GPT需要用[A]预测B, 用[A, B]预测C, 用[A, B, C]预测D。很显然的就是当要预测B时, 需要将[B, C, D]遮掩起来。
具体的遮掩操作是在slef-attention进行softmax之前进行的, 一般的实现是将MASK的位置用一个无穷小的数值-inf来替换, 替换后执行softmax计算得到新的结果矩阵,这样-inf的位置就变成了0。如上图所示, 最后的矩阵可以很方便的做到当利用A预测B的时候, 只能看到A的信息; 当利用[A, B]预测C的时候, 只能看到A, B的信息。
注意:对比于经典的Transformer架构, 解码器模块采用了6个Decoder Block; GPT的架构中采用了12个Decoder Block。
5.3 GPT训练过程
GPT的训练也是典型的两阶段过程:
-
第一阶段: 无监督的预训练语言模型
-
第二阶段: 有监督的下游任务fine-tunning
5.3.1 无监督的预训练语言模型
给定句子U = [u1, u2, ..., un], GPT训练语言模型时的目标是最大化下面的似然函数:
其中,$$u_i$$ 是第 $$i$$ 个单词,$$Θ$$ 是模型参数。
有上述公式可知, GPT是一个单向语言模型, 假设输入张量用$$h_0$$表示, 则计算公式如下:
其中$$W_p$$是单词的位置编码, $$W_e$$是单词本身的word embedding,$$W_p$$的形状是[max_seq_len, embedding_dim],$$W_e$$的形状是[vocab_size, embedding_dim]。
得到输入张量$$h_0$$后, 要将$$h_0$$传入GPT的Decoder Block中, 依次得到$$h_t$$:
最后通过得到的$$h_t$$来预测下一个单词:
5.3.2 有监督的下游任务fine-tunning
GPT经过预训练后, 会针对具体的下游任务对模型进行微调. 微调采用的是有监督学习, 训练样本包括单词序列[x1, x2, ..., xn]和label y。GPT微调的目标任务是根据单词序列[x1, x2, ..., xn]预测标签y。
其中$$W_y$$表示预测输出的矩阵参数, 微调任务的目标是最大化下面的函数:
综合两个阶段的目标任务函数, 可知GPT的最终优化函数为:
其中,$$L_2$$ 是任务特定的损失函数,$$L_1$$ 是语言模型的损失函数,$$λ$$ 是权重系数。
5.4 小结
-
什么是GPT
-
GPT是OpenAI 提出的基于Transformer的自回归(Autoregressive)生成模型
-
本质上来说, GPT是一个单向语言模型
-
-
GPT的架构
-
GPT采用了Transformer架构中的解码器模块
-
GPT在使用解码器模块时做了一定的改造, 将传统的3层Decoder Block变成了2层Block, 删除了encoder-decoder attention子层, 只保留Masked Multi-Head Attention子层和Feed Forward子层
-
GPT的解码器总共是由12个改造后的Decoder Block组成的
-
-
GPT的预训练任务
-
第一阶段: 无监督的预训练语言模型,只利用单词前面的信息来预测当前单词
-
第二阶段: 有监督的下游任务fine-tunning
-
六、BERT GPT ELMo模型对比
6.1 BERT、GPT、ELMo之间的不同点
-
关于特征提取器:
-
ELMo采用两部分双层双向LSTM进行特征提取, 然后再进行特征拼接来融合语义信息。
-
BERT采用的是Transformer架构中的Encoder模块。
-
GPT采用的是Transformer架构中的Decoder模块。
-
很多NLP任务表明Transformer的特征提取能力强于LSTM, 对于ELMo而言, 采用1层静态token embedding + 2层LSTM, 提取特征的能力有限。
-
-
单/双向语言模型:
-
三者之中, 只有GPT采用单向语言模型, 而ELMo和BERT都采用双向语言模型。
-
ELMo虽然被认为采用了双向语言模型, 但实际上是左右两个单向语言模型分别提取特征, 然后进行特征拼接, 这种融合特征的能力比BERT一体化的融合特征方式弱。
-
三者之中, 只有ELMo没有采用Transformer。GPT和BERT都源于Transformer架构, GPT的单向语言模型采用了经过修改后的Decoder模块, Decoder采用了look-ahead mask, 只能看到context before上文信息, 未来的信息都被mask掉了。而BERT的双向语言模型采用了Encoder模块, Encoder只采用了padding mask, 可以同时看到context before上文信息, 以及context after下文信息。
-
6.2 BERT、GPT、ELMo各自的优点和缺点
ELMo模型:
-
优点:
-
从早期的Word2Vec预训练模型的最大缺点出发, 进行改进, 这一缺点就是无法解决多义词的问题。
-
ELMo根据上下文动态调整word embedding, 可以解决多义词的问题。
-
-
缺点:
-
ELMo使用LSTM提取特征的能力弱于Transformer。
-
ELMo使用向量拼接的方式融合上下文特征的能力弱于Transformer。
-
GPT模型:
-
优点:
-
GPT使用了Transformer提取特征, 使得模型能力大幅提升。
-
-
缺点:
-
GPT只使用了单向Decoder, 无法融合未来的信息。
-
BERT模型:
-
优点:
-
BERT使用了双向Transformer提取特征, 使得模型能力大幅提升。
-
添加了两个预训练任务, MLM + NSP的多任务方式进行模型预训练。
-
-
缺点:
-
模型过于庞大, 参数量太多, 需要的数据和算力要求过高, 训练好的模型应用场景要求高。
-
更适合用于语言嵌入表达, 语言理解方面的任务, 不适合用于生成式的任务。
-
6.3 小结
BERT, GPT, ELMo之间的区别:
-
三者所选取的特征提取器不同
-
BERT采用的是Transformer架构中的Encoder模块
-
GPT采用的是Transformer架构中的Decoder模块
-
ELMo采用的双层双向LSTM模块
-
-
三者所采用的语言模型单/双向不同
-
BERT采用的是最彻底的双向语言模型, 可以同时关注context before和context after。
-
GPT采用的是单向语言模型, 即Transformer中的Decoder, 由于采用了mask机制, 所以未来信息context after都不可见。
-
ELMo表面上被认为是双向语言模型, 但实际上是左右两个单向LSTM模型分别提取特征, 在进行简单的拼接融合。
-