©PaperWeekly 原创 · 作者 |苏剑林
单位 |追一科技
研究方向 |NLP、神经网络
两年前,在《万能的seq2seq:基于seq2seq的阅读理解问答》和《“非自回归”也不差:基于MLM的阅读理解问答》中,我们在尝试过分别利用“Seq2Seq+前缀树”和“MLM+前缀树”的方式做抽取式阅读理解任务,并获得了不错的结果。而在去年的 ICLR 2021上,Facebook 的论文《Autoregressive Entity Retrieval》同样利用“Seq2Seq+前缀树”的组合,在实体链接和文档检索上做到了效果与效率的“双赢”。
事实上,“Seq2Seq+前缀树”的组合理论上可以用到任意检索型任务中,堪称是检索任务的“新范式”。本文将再次回顾“Seq2Seq+前缀树”的思路,并用它来实现最近推出的 KgCLUE 知识图谱问答榜单的一个 baseline。
检索任务
说到检索任务,想必大家都不陌生,除了常规的相似问检索外,NLP中还有很多任务都可以视为检索,比如抽取式阅读理解、实体链接甚至基于知识图谱的问答,等等。
以相似问检索为例,常规的检索系统的流程为:
1. 训练句子编码模型,这通常包含复杂的负样本构建流程,负样本质量直接影响到最终效果;
2. 将每个句子编码为向量,存到诸如Faiss的向量检索库中,这一步通常需要消耗相当大的空间;
3. 将查询句子编码为向量,然后进行检索,返回 Topk 结果及其相似度。
如果现在告诉你,有一个做检索的新方案,可以不用花心思挑选负样本,也不用消耗极大内存的向量检索库,最终效果和速度也不差于旧方案,那你会不会迫不及待想要尝试一下?没错,这就是本文的主角“Seq2Seq+前缀树”了。
首先,让我们抛开各种繁琐的细枝末节,想一想检索任务究竟在做什么。对于相似问检索来说,我们输入一个问句,希望输出数据库中与之最相近的句子;对于实体链接来说,我们输入一个包含该实体的句子,希望输出知识库中能正确诠释该实体的实体名或者编号;等等。
抛开某些约束规则不说,可以发现这些任务本质上都可以抽象为:输入一个句子,输出另一个句子。
这不正是 Seq2Seq 最擅长的工作了嘛!所以用 Seq2Seq 做不是一件很自然的事情?当然,有读者会说我要输出的是数据库里边已有的一个句子呀,Seq2Seq 要是“溢出”(解码出了数据库不存在的句子)了怎么办?这时该前缀树上场了,我们可以利用前缀树约束解码过程,保证生成的结果在数据库中,这一点我们等会细说。
没有了“溢出”的顾虑,我们将会发现 Seq2Seq 的做法真的是集诸多优点于一身,比如:
1. 训练 Seq2Seq 模型只需要输入和目标,这也就是说我们只需要正样本,免除了构建负样本的烦恼,或者说它是将所有其他句子都当成负样本了;
2. Seq2Seq 是直接解码出目标句子,省去了句向量的储存和检索,也就免除了 Faiss 等工具的使用了;
3. Seq2Seq 包含了目标句子与输入句子之间 Token 级别的交互,理论上比基于内积的向量检索能做到更精细的对比,从而有更好的检索效果。
▲ 前缀树示意图:本质上是序列的一种压缩表示
有了前缀树,我们约束 Seq2Seq 解码就不困难了,比如第一个字只能是“明”或“今”,那么在预测第一个字的时候,我们可以把模型预测其他字的概率都置零,这样模型只可能从这两个字中二选一;如果已经确定了第一个字,比如“明”,那么我们在预测第二个字的时候,同样可以将“月”、“天”或“年”以外的字的概率都置零,这样模型只可能从这三个字中选一个,结果必然是“明月”、“明天”、“明年”之一;依此类推,通过将不在前缀树上的候选 token 置零,保证解码过程只走前缀树的分支,而且必须走到最后,这样解码出来的结果必然是数据库中已有的句子。
相比常规的向量检索方案,“Seq2Seq+前缀树”的方案用前缀树代替了要储存的检索向量,而前缀树本质上是原始句子的一种“压缩表示”,所以不难想象前缀树所需要的储存空间要比稠密的检索向量要少得多。在 Python 中,实现前缀树比较简单的方案就是利用字典结构来实现嵌套,具体例子可以参考后面的 KgCLUE 的代码。
实践是检验真理的唯一标准,现在我们就利用“Seq2Seq+前缀树”的方案实现一个 KgCLUE 的 baseline,以检验它的有效性。
KgCLUE 是 CLUE 组织最近推出的一个中文知识图谱问答的评测任务,数据比较规范,适合科研实验测试。具体来说,它以约 2000 万个三元组为知识库,每个三元组是 (S, P, O) 的格式(Subject-Predicate-Object),如下图:
然后它还提供了一批标注语料供训练,每个样本是简单的问题加答案的形式,其实问题本质上都可以抽象为“S 的 P 是什么”,而答案则是对应的三原则 (S,P,O),如下图:
原则上来说,只要确定了 (S,P),就可以从知识库里边抽取出对应的 O,所以我们主要的任务,就是要从问题中解析出正确的 S 和 P 出来。
但要注意的是,知识库里边可能存在很多同名实体,比如“牛郎织女”,可能指神话故事,也可能指一本书或者一首歌等,为了对它们进行区分,知识库里边还有一个“义项(Meaning)”的概念,用来注明该名词的具体指代,在 KgCLUE 的知识库中,义项是通过括号的方式补充在 Subject 后面,比如“牛郎织女(中国著名民间故事)”、“牛郎织女(2015 年东方出版社出版的图书)”等,但如果直接从问题抽取的话,通常只能抽取到义项以外的部分,即“牛郎织女”,所以我们实际处理时,通常会将它们分隔开,即将每条知识视为一个四元组 (S, M, P, O) 而不是三元组。
根据给定问题来确定 Subject 究竟属于哪个 Meaning,这就是“实体链接”问题,是知识图谱问答的必要步骤。但如果局限在当前的 KgCLUE 任务中,由于语料本身不大,对于分两步的模型来说,我们可以认为实体链接这一步整合到了相似度模型中,而不单独进行实体链接任务。
4.3 本文方案
如果用“Seq2Seq+前缀树”来做的话,那么模型训练方面将会变得非常简单。
具体来说,我们就只需要一个 Seq2Seq 模型,然后将问题当作 Seq2Seq 的输入,将 (S,P,M) 用 [SEP] 连接起来作为目标,进行正常的 Seq2Seq 训练就行了。这里的一个技巧是按照 (S,P,M) 的顺序进行拼接,要比按照 (S,M,P) 的顺序的最终效果要好很多(8~10 个百分点),这是因为问题来预测 S,P 要比预测 M 都更容易,我们要先把容易预测的预测出来,以减少候选答案的数量。
在参考代码中,我们所用的 Seq2Seq 模型是《SimBERTv2来了!融合检索和生成的RoFormer-Sim模型》、《用开源的人工标注数据来增强RoFormer-Sim》中介绍的 RoFormer-Sim-FT 模型,它是利用 UniLM 模型预训练过的相似问生成模型,经过对比,用 RoFormer-Sim-FT 相比直接用 RoFormer,效果至少提升 2 个百分点。这也说明相似问生成是该方案的一种有效的预训练方式。
4.4 错例分析
解码的时候,我们先把所有的 (S,P,M) 建立成前缀树,然后按照前缀树进行解码,就保证了解码结果必然落到知识库的某个三元组中,从而能够合理地输出结果。详细的前缀解码步骤前面已经介绍过了,这里就不再细说。
然而,观察 bad case 的时候,发现模型有可能会出现一些非常“简单”的 bad case,比如“海浦东香格里拉大酒店离火车站有多远?”,正确的 (S,P) 应该是“(上海浦东香格里拉大酒店, 火车站距离)”,但模型却生成了“(上海浦东香格里拉大酒店, 酒店星级)”;有时候问“XXX 讨厌什么”,结果模型却生成了“(XXX, 喜欢)”;有时候问“XXX 主要讲什么课程”,正确的答案应该是“(XXX, 主讲课程)”,结果模型却生成了“(XXX, 主要成就)”。也就是说,模型似乎会在一些字面上看起来非常简单的问题上犯错(生成错误的 P)。
经过思考,笔者认为这种 bad case 本质上是 Seq2Seq 本身的固有缺点所导致的,主要包含两方面:1)训练时的 Exposure Bias 问题;2)解码时 Beam Search 的贪心问题。
首先,由于 Seq2Seq 在训练时是已知上一真实标签的,这会弱化训练难度,导致模型的“全局观”不够;其次,解码哪怕用了 Beam Search,本质上也是贪心的,很难做到综合后几个 token 来预测当前 token。比如刚才的“XXX 主要讲什么课程”一例,模型生成 P 的时候,首先就很贪心地生成“主要”两个字,然后按照前缀树的约束,“主要”后面只能接“成就”了(因为“主讲课程”前两个字是“主讲”),所以就出来了“主要成就”。
理论上,应用一些缓解 Seq2Seq 的 Exposure Bias 问题的策略,比如《Seq2Seq中Exposure Bias现象的浅析与对策》、《TeaForN:让Teacher Forcing更有“远见”一些》等,应该是对此问题有帮助的。这些方法比较多,复杂度也有所不一样,就留给读者自行尝试了。
4.5 “前瞻”策略
这里笔者提出另一个能够缓解此问题的“前瞻”策略。
在“Seq2Seq+前缀树”方案中,我们的 Seq2Seq 不是真的要去生成任意文本,而是在前缀树的约束下做本质上是检索的操作,所以生成了 S 之后,我们可以知道后续容许的 P,并且一般来说后续容许的 P 不会太多,所以我们可以直接逐一枚举容许的 P,通过 P 对问题的覆盖程度,来调整当前 token 的预测结果。
https://github.com/bojone/KgCLUE-bert4keras
目前排行榜上排名第二:
调试历程大概是:
1. 开始用 RoFormer+UniLM 按照 (S,M,P) 顺序预测,验证集 EM 大约是 70 多;
2. 然后改为 (S,P,M) 的顺序之后,验证集能做到 82 了;
3. 接着预训练模型换用 RoFormer-Sim-FT 后,提升到 84~85;
4. 最后加上“前瞻”策略,就做到当前的 89 了。
最典型的问题,就是 Seq2Seq 本身的固有问题,这我们在前面已经提过了。虽然“前瞻”策略已经能给我们带来不错的提升,但相应的问题依然没有完全解决,如何更自然地解决该问题,或者设计更自然的解码规则,依然是值得思考,没有标准答案。此外,前面提到的解决 Exposure Bias 问题的通用策略,笔者也还没有尝试,不确定具体效果如何。
还有一个问题,就是“Seq2Seq+前缀树”的方案,是靠模型把结果“生成”的,而一旦遇到生僻字被识别为 [UNK],那么大概率就会失败了,尤其是如果 S 的第一个字就是 [UNK],那么几乎都会失败,所以如何更好地解决 [UNK] 问题,是一个值得研究的问题。当然,也可以尝试传统的 Copy 机制,这就看个人的审美了。
最后,“Seq2Seq+前缀树”或许可以在评测指标上取得不错的效果,但它对于工程来说,有一个不大有好的特点,就是修正 bad case 会变得比较困难,因为传统方法修正 bad case,你只需要不断加样本就行了,而“Seq2Seq+前缀树”则需要你修改解码过程,这通常困难得多。
特别鸣谢
感谢 TCCI 天桥脑科学研究院对于 PaperWeekly 的支持。TCCI 关注大脑探知、大脑功能和大脑健康。
更多阅读
#投 稿 通 道#
让你的文字被更多人看到
如何才能让更多的优质内容以更短路径到达读者群体,缩短读者寻找优质内容的成本呢?答案就是:你不认识的人。
总有一些你不认识的人,知道你想知道的东西。PaperWeekly 或许可以成为一座桥梁,促使不同背景、不同方向的学者和学术灵感相互碰撞,迸发出更多的可能性。
PaperWeekly 鼓励高校实验室或个人,在我们的平台上分享各类优质内容,可以是最新论文解读,也可以是学术热点剖析、科研心得或竞赛经验讲解等。我们的目的只有一个,让知识真正流动起来。
📝 稿件基本要求:
• 文章确系个人原创作品,未曾在公开渠道发表,如为其他平台已发表或待发表的文章,请明确标注
• 稿件建议以 markdown 格式撰写,文中配图以附件形式发送,要求图片清晰,无版权问题
• PaperWeekly 尊重原作者署名权,并将为每篇被采纳的原创首发稿件,提供业内具有竞争力稿酬,具体依据文章阅读量和文章质量阶梯制结算
📬 投稿通道:
• 投稿邮箱:hr@paperweekly.site
• 来稿请备注即时联系方式(微信),以便我们在稿件选用的第一时间联系作者
• 您也可以直接添加小编微信(pwbot02)快速投稿,备注:姓名-投稿
△长按添加PaperWeekly小编
🔍
现在,在「知乎」也能找到我们了
进入知乎首页搜索「PaperWeekly」
点击「关注」订阅我们的专栏吧