赞
踩
转载来源:https://zhuanlan.zhihu.com/p/146325984
20 世纪以来,自然语言处理(NLP)领域的发展涌现了许多创新和突破。NLP 中许多之前机器不可能完成的任务,如阅读理解、人机对话、自动写新闻稿等,正逐渐成为现实,甚至超越了人类的表现。
如果总结过去 20 年里,无数先辈辛劳付出带来的璀璨成果,以下 3 个代表性工作列入 NLP 名人堂,应该实至名归:
1)2003 年 Bengio 提出神经网络语言模型 NNLM,从此统一了 NLP 的特征形式——Embedding;
2)2013 年 Mikolov 提出词向量 Word2vec,延续 NNLM 又引入了大规模预训练(Pretrain)的思路;
3)2017 年 Vaswani 提出 Transformer 模型,实现用一个模型处理多种 NLP 任务。
基于 Transformer 架构,2018 年底开始出现一大批预训练语言模型,刷新众多 NLP 任务,形成新的里程碑事件。本文将跨越 2018-2020,着眼于 3 个预训练代表性模型 BERT、XLNet 和 MPNet,从以下 4 个章节介绍 NLP 预训练语言模型的发展变迁史:
- 1.BERT 原理及 MLM 简述
- 2.XLNet 原理及 PLM 简述
- 3.MPNet 原理及创新点简述
- 4.NLP预训练模型趋势跟踪
- 附录:快速上手BERT的4大工具包
自谷歌 2018 年底开源 BERT,NLP 界的游戏规则某种程度上被 “颠覆” 了;一时间,这个芝麻街的可爱小黄人形象,成为众多 NLPer 及其他 DL、ML 研究者们的拥趸。
“BERT 一把梭 “,“遇事不决就 BERT”,“BERT 在手,天下我有”,表达了使用者们对 BERT 的心声。也因为 BERT,NLP 的准入门槛大幅下降,一些较浅层的 NLP 任务如文本分类、相似匹配、聚类某种程度上可以被认为是完全解决。
BERT 四大下游任务微调
BERT 为什么会有如此引人注目的优良效果?下面我们再来回顾下 BERT 到底是什么。
BERT 本质上是一个自编码(Auto Encoder)语言模型,为了能见多识广,BERT 使用 3 亿多词语训练,采用 12 层双向 Transformer 架构。注意,BERT 只使用了 Transformer 的编码器部分,可以理解为 BERT 旨在学习庞大文本的内部语义信息。
具体训练目标之一,是被称为掩码语言模型的 MLM。即输入一句话,给其中 15% 的字打上 “mask” 标记,经过 Embedding 输入和 12 层 Transformer 深度理解,来预测 “mask” 标记的地方原本是哪个字。
- input: 欲把西[mask]比西子,淡[mask]浓抹总相宜
- output: 欲把西[湖]比西子,淡[妆]浓抹总相宜
例如我们输入 “欲把西 [mask] 比西子,淡 [mask] 浓抹总相宜” 给 BERT,它需要根据没有被 “mask” 的上下文,预测出掩盖的地方是 “湖” 和“妆”。
MLM 任务的灵感来自于人类做完形填空。挖去文章中的某些片段,需要通过上下文理解来猜测这些被掩盖位置原先的内容。
训练目标之二,是预测输入的两句话之间是否为上下文(NSP)的二分类问题。继续输入 “欲把西[湖] 比西子,淡 [妆] 浓抹总相宜”,BERT 将预测这两句话的组合是否合理(这个例子是“yes”)。(随后的研究者对预训练模型探索中证明,NSP 任务过于简单,对语言模型的训练作用并不是很大)
通过这两个任务和大规模语料训练,BERT 语言模型可以很好学习到文本之间的蕴含的关系。
接下来简单介绍 BERT 以及 XLNet、MPNet 所使用 Transformer 的核心模块:自注意力机制。
自注意力机制重点在于学习输入序列自身的内部信息。具体地,每个 tokentokentoken 可以观察到序列中其他所有 tokentokentoken 的信息,并通过” 注意力 “交互,其余的 token′token'token′ 会产生不同大小地权重(整个过程类似加权)。上例中,“西子”和 “西湖” 关系紧密,因此它们之间的 attention 权重更大(大于 “西子” 和“淡妆”)。最终自注意力层的输出涵盖了序列所有 tokentokentoken 的语义信息,实现了双向编码上下文。
同时,这种双向性使得模型可以同时观测序列的所有位置,解决了 RNN 等递归模型无法高效并行的瓶颈。
由于架构采用 12 层双向 Transformer 且训练目标包含还原 maskmaskmask 位置的信息,BERT 被称为去噪自编码语言模型(DAE)。
而在 BERT 之前,NLP 领域的语言模型几乎是 Auto Regression(自回归)类型,即当前位置的字符预测 TiTiTi需要编码之前 T(0:i−1)T(0:i-1)T(0:i−1) tokens 的语义信息,使得模型训练 / 预测只能单向进行。
虽然 ELMO 采用了 BiLSTM,但只是前向、后向两次输出的简单拼接,包含的全局语义信息依然较弱。
虽然效果好,BERT 的缺点也很明显。从建模本身来看,随机选取 15% 的字符 mask 忽视了被 mask 字符之间可能存在语义关联的现象,从而丢失了部分上下文信息。同时,微调阶段没有 mask 标记,导致预训练与微调的不一致。
和 BERT 不同,XLNet 本质上是用自回归语言模型来同时编码双向语义信息的思路,可以克服 BERT 存在的依赖缺失和训练 / 微调不一致的问题。同时为了弥补自回归模型训练时无法同时看到上下文的缺陷,XLNet 曲线救国地提出了 PLM 排列语言模型的训练方式。
对于一个长度为 N 的序列,我们知道其存在 N!N!N! 种因式分解顺序,通过一次采样一种序列的因式分解组合,每个 token 总是能够在不同的序列中观察到其他所有 token;同时模型参数对于所有的因式分解顺序共享,因此从期望的角度上看,XLNet 模型能够双向地编码上下文。
例如,初始序列为 (x1,x2,x3,x4)(x1,x2,x3,x4)(x1,x2,x3,x4),这里的 x3x3x3 只能关注到前面的 (x1,x2)(x1,x2)(x1,x2) ,但在某种因式分解排列(x4,x2,x1,x3)(x4,x2,x1,x3)(x4,x2,x1,x3)中, x3x3x3 具备了关注 (x4,x2,x1)(x4,x2,x1)(x4,x2,x1)的能力。另外,XLNet 的原始输入和 BERT 相同,依然是正常排序的(x1,x2,x3,x4)(x1,x2,x3,x4)(x1,x2,x3,x4) 。
那 XLNet 是如何在保持输入顺序不变的同时,对序列进行乱序编码的呢?
简单而言,通过 Attention 掩码机制,将当前 token 及其之后的 token(不该看到的部分)嵌入信息用 attention-mask 掩盖。具体实现上,使用了一种双流自注意力机制。
例如某个序列的因式分解顺序为 (x2,x1,x4,x3)(x2,x1,x4,x3)(x2,x1,x4,x3) 和 (x2,x1,x3,x4)(x2,x1,x3,x4)(x2,x1,x3,x4),如果需要预测第三个位置的 token,传统的自回归模型通过 (x2,x1)(x2,x1)(x2,x1) 的编码来预测后面的 token,概率表达式为 P(xt∣(x2,x1))P(xt|(x2,x1))P(xt∣(x2,x1))。然而这样会带来一个问题:x2 和 x1 的编码和需要预测的下一个 token 是无关的,xt 既可以是 x4 也可以是 x3,即 P(x3|x2,x1) = P(x4|x2,x1),这显然不合理(传统 RNN 是按正常的序列进行递归预测,位置是正确的,所以不存在这个问题)。因此 XLNet 需要引入待预测 token 的位置信息,例如 P(x4∣x2,x1,pos4)P(x4|x2,x1,pos4)P(x4∣x2,x1,pos4) 或 P(x3∣x2,x1,pos3)P(x3|x2,x1,pos3)P(x3∣x2,x1,pos3) ,确保生成合理的结果。
然而这又带来了新的矛盾。对于某个因式分解顺序 (x2,x1,x4,x3)(x2,x1,x4,x3)(x2,x1,x4,x3),在预测 x4 的时候,模型不能编码自身的 token-embedding,只能编码前面的 (x2,x1)(x2,x1)(x2,x1)以及自身的 position-embedding,否则训练就没有意义了;然而在预测 x3 的时候,又需要用到 x4 的完整的编码信息。如果继续沿用 BERT 的自注意力机制必然存在问题,因此 XLNET 将自注意力机制拆分为 Query 流和 Content 流。Query 流中当前 token 只能关注到前面的 token 和自身的位置信息,Content 流中当前 token 可以关注到自身。
具体来看,XLNET 将序列拆分为 2 部分,序列的后部分(约占句长的 1/K,K 为超参数)为需要预测的部分,前部分为已知上下文。已知的上下文不做预测,因此只计算 content 流注意力,每个 token 都编码之前 token 以及自身的完整信息。从预测部分开始,每个 token 同时计算 Query 流和 Content 流注意力:Query 流的输出用于预训练做预测,Content 流的输出提供给后续待预测 token 计算 Query 流,这就保证了当预测当前 token 时,它无法看到自身编码;当前 token 预测结束后,将其 Content 流作为上下文部分的编码提供给后续需要预测的 token。预训练过程计算 2 种注意力,微调过程去除了 Query 流,只保留 Content 流,因为不需要对 token 进行词表空间的预测,而是需要编码整个上下文语义用于下游任务。
前面提到 Auto Regression 模型的缺点是只能单向编码,但它能够编码被预测的 token 之间的联系,即克服了 BERT 被 mask 字符间信息丢失的缺点。其次,通过上文的 PLM 模型弥补了自回归语言模型只能单向编码的缺点。AR 模型在预训练和下游任务中都没有对输入序列进行损坏(遮盖部分 token,引入噪声),消除了模型在预训练和微调过程中的差异。
虽然在期望上看,PLM 几乎实现了双向编码功能的自回归模型,但是针对某一个因式分解序列来说,被预测的 token 依然只能关注到它前面的序列,导致模型依然无法看到完整序列信息和位置信息。
结合 BERT、XLNet 的思路,南京大学和微软在 2020 年共同提出了新的预训练语言模型 MPNet:Masked and Permuted Pre-training for Language Understanding。
MPNet 的创新点在于 4 个字:位置补偿(position compensation),大家先留个印象,下文会再详细介绍。
论文开篇,作者针对上文 MLM、PLM 各自特点,希望用一种统一的模型既保留二者的优点,又弥补它们的不足,这就是 MPNet。
MLM、PLM 回顾,(a)、(b) 中左边和右边等价
首先,作者通过重新排列和切分输入序列中的 tokens,将 MLM 和 PLM 统一为非预测部分(non-predicted)和预测部分(predicted),如图 (a),(b) 右侧。如此一来,MLM 和 PLM 就拥有了相似的数学表达公式,仅在条件部分有细小差异。
为缓解 BERT-mask 可能丢失依赖信息的问题,MPNet 沿用了 XLNet 的自回归结构,同时为弥补 XLNet 无法捕捉全部序列位置信息的缺陷,添加了「位置补偿」:针对需要预测的 token,额外添加了它们的位置信息。使得自回归过程中,在任意一个位置 i,除了可以看到之前部分的 token 编码,还能看到序列所有 token 的位置编码(类似于 BERT)。
例如,对于一个长度为 6 的 token 序列 x=(x1,x2,x3,x4,x5,x6)x=(x 1, x 2, x 3, x 4, x 5, x 6)x=(x1,x2,x3,x4,x5,x6),采样得到一个因式分解序列 xz=(x1,x3,x5,x4,x6,x2)x z=(x 1, x 3, x 5, x 4, x 6, x 2)xz=(x1,x3,x5,x4,x6,x2);假设非预测部分为 c=3,x(z<=c)=(x1,x3,x5)c=3,x(z<=c)=(x1,x3,x5)c=3,x(z<=c)=(x1,x3,x5),待预测部分为 x(z>c)=(x4,x6,x2)x(z>c)=(x4,x6,x2)x(z>c)=(x4,x6,x2) 。对于 z>cz>cz>c部分,作者在待预测的 tokens 左边额外添加了 mask-token M(z>c)M(z>c)M(z>c),最终整个 token 的输入序列由三部分组成:(x(z<=c),M(z>c),x(z>c))=(x1,x3,x5,[M],[M],[M],x4,x6,x2)(x(z<=c), M(z>c), x(z>c))=(x 1, x 3, x 5,[M],[M],[M], x 4, x 6, x 2)(x(z<=c),M(z>c),x(z>c))=(x1,x3,x5,[M],[M],[M],x4,x6,x2) ,[M] 表示遮盖该 token;对应的位置序列为:(z(<=c),z(>c),z(>c))=(p1,p3,p5,p4,p6,p2,p4,p6,p2)(z(<=c), z(>c), z(>c))=(p 1, p 3, p 5, p 4, p 6, p 2, p 4, p 6, p 2)(z(<=c),z(>c),z(>c))=(p1,p3,p5,p4,p6,p2,p4,p6,p2)。
3 个 [M] 和对应位置 position-embedding 的加入,就是位置补偿。例如在序列 (x1,x3,x5,[M],[M],[M],x4,x6,x2)(x 1, x 3, x 5,[M],[M],[M], x 4, x 6, x 2)(x1,x3,x5,[M],[M],[M],x4,x6,x2)中预测 x4x4x4时,不仅能看到 (x1,x3,x5)(x1,x3,x5)(x1,x3,x5)的 token-embedding,还能看到 (x1,x3,x5,x4,x6,x2)(x1,x3,x5,x4,x6,x2)(x1,x3,x5,x4,x6,x2)的 position-embedding;依次递归预测 (x6,x2)(x6,x2)(x6,x2) 。
MPNet 使用自回归编码,避免了 BERT 做 Mask 时可能丢失被 Mask 的 token 的彼此关联信息和 pretrain(有 mask)、finetune(无 mask)不一致的问题;通过位置补偿,又解决了 XLNet 无法看到全局位置信息的缺陷。取其精华,确实是挺巧妙的一种思路。
观察输入信息的占比,MPNet 输入的信息量是最大的;从直观上理解,模型每次可以接受到更多的文本特征,从而容易训练出更优结果。
作者在权威的语义理解评估数据集 GLUE 上的实验结果表面,MPNet 确实比它的前辈 BERT 和 XLNet 略胜一筹。另外,作者表示 MPNet 在训练时加入了全词掩码 whole word mask 以及相对位置编码等已被证明有效的 trick,加上和 RoBERTa 训练一样的 160GB 训练语料,取得这样的结果应该说是情理之中了。
末尾的消融实验,可以看到位置补偿和 PLM 对实验结果的提升都很关键。
从目前来看,大规模语料预训练 + finetune 的方式,应该会是 NLP 接下去几年的主流。各种基于语言模型的改进也是层出不穷。虽然玩法种类各异,我们还是可以瞥见一些具有突破性的方向。
前期 BERT 到 RoBERTa,GPT 到 GPT2 效果的提升,已经证明更多数据可以跑出更强大更通用的预训练模型。去年底到今年,英伟达、谷歌、Open-AI 相继放出巨无霸模型 MegatronLM(83 亿参数)、T5(110 亿)、GPT3(1500 亿),不断刷榜令人咋舌的同时也彰显了巨头们的实力。
相信未来,巨无霸模型依然会成为大公司的研究目标之一,却让普通科研人员可望不可及。
没有前排巨头们的经济实力,普通公司和科研机构沿着相反赛道 - 模型轻量化下足了功夫。如何在尽可能少的参数量下,取得和大模型接近的效果,同时训练 / 预测速度翻倍,是很实际很有价值的课题。
这其中,有代表性的工作如华为诺亚方舟实验室发布的 TinyBERT、北大的 FastBERT 都取得了瞩目的效果。例如 FastBERT 在 BERT 的每一层都接入一个分类器,通过样本自适应机制自动调整每个样本的计算量(容易的样本通过一两层就可以预测出来,较难的样本则需要走完全程)。
图中 “Speed” 代表不确定性的阈值,和推理速度成正比。在 Speed=0.2 时,FastBERT 速度可以提升 1-10 倍,且精度下降全部在 0.11 个点之内。
除了知识蒸馏,常规的模型轻量化一般包含层数裁剪、精度量化等手段。
在实际业务场景中,对于中小 AI 企业往往容易出现数据量不足的问题。例如用户需要订制一个 FAQ 问答机器人,有 100 个标准问,但表示每个问句只有 2-3 条同义句…
战略上,“客户就是上帝 “的精神激励我们不能虚,要迎难而上。战术上,除了花高成本找标注团队造数据外,迁移学习、小样本学习可能会非常有帮助。受到人类具有快速从少量(单)样本中学习能力的启发(例如生活在北方的人可能没有见过榴莲,一旦看过一次榴莲的照片,就认识了!),让模型在少量样本中学习获得有力的泛化能力,成为近年的研究热点之一。
感兴趣的同学可以参考阿里的这篇 paper:Few-Shot Text Classification with Induction Network。
预训练语言模型的代表 BERT,已经成为 NLP 领域的重要工具,不同机构 / 个人也分别开发了轻松使用 BERT 的工具包。笔者结合自身经验,简单概括了一下:
5.1 肖涵 - bert-as-service
顾名思义,将 BERT 模型直接封装成一个服务,堪称上手最快的 BERT 工具。作者是 xxx 肖涵博士。
按照 GIthub 上的教程,下载 BERT 权重并安装工具包,三行代码即可轻松使用 BERT 获得文本的向量特征,完成下游 NLP 各项任务。bert-as-service 是跨平台的服务,不受限于 OS、深度学习框架,且作者对于并发做了大量优化与加速,可以满足日常实验甚至公司的实际业务需求。
5.2 Google - BERT 源码
BERT 源码官方仓库,可以学习 BERT 各模块的底层实现细节。Google 开源了权重的同时,也开源了预训练、子任务微调的脚本,是学习 BERT 不可略过的学习教程。代码基于 tensorflow,对 TF 熟练的同学会更快上手。
当前,仓库中还发布了 2/4/6/8… 层不同大小的 BERT,以缓解 BERT 资源开销大、inference 缓慢带来的问题。中文 BERT 可以参考哈工大崔一鸣、实在智能徐亮等开源的权重。
5.3 huggingface - transformers
有了 TF 版,pytorch 怎甘落后。机构 huggingface 开发的 transformers 工具包,堪称预训练模型大礼包,囊括了 10 几种火热模型。
种类齐全且 api 接口实现统一、调用简单,是 pytorch 框架与 BERT 的最佳组合。transformers 的 src 源码也是学习 BERT 等模型原理的绝佳资料。
5.4 苏剑林 - bert4keras
接下来自然而然该 Keras 出场了!作为 tf2.0 的官方高阶 api,Keras 的简洁特性始终拥有超高人气。
来自追一科技的苏神苏剑林,在业余时间自己实现了 bert4keras 框架,且提供了详细教程、众多下游任务微调脚本(分类、文本生成、QA、图片标题生成等)。始终走在 BERT 任务的前沿。
除以上工具包,github 上还有众多用户开源的 BERT 相关工具,按需参考使用即可。
[1] Devlin J, Chang M W, Lee K, et al. BERT: Pre-training of Deep Bidirectional Transformers for Language Understanding[J]. arXiv preprint arXiv:1810.04805, 2018.
[2] Vaswani A, Shazeer N, Parmar N, et al. Attention is all you need [C]//Advances in Neural Information Processing Systems. 2017: 5998-6008.
[3]Zhilin Yang, Zihang Dai, Yiming, et.al. XLNet: Generalized Autoregressive Pretraining for Language Understanding[C]. arXiv preprint arXiv:1906.08237, 2019.
[4]Kaitao Song, Xu Tan, Tao Qin, Tie-Yan Liu, et.al. MPNet: Masked and Permuted Pre-training for Language Understanding [C]. arXiv preprint arXiv:2004.09297, 2020.
[5]Weijie Liu, PengZhou, QiJu, et.al. FastBERT: a Self-distilling BERT with Adaptive Inference Time[C]. arXiv preprint arXiv:2004.02178, 2020.
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。