Pretrain, Prompt and Predict, A Systematic Survey of Prompting Methods in NLP

论文:[2107.13586] Pre-train, Prompt, and Predict: A Systematic Survey of Prompting Methods in Natural Language Processing

Code:无

一句话概述:想办法在输入和标签之间搭一座桥。

摘要:与传统有监督学习不同的是,基于 Prompt 的学习基于语言模型直接对文本的概率进行建模。具体来说,为了使用这些模型执行预测任务,使用模板将原始输入 x 修改为具有一些未填充槽的文本字符串提示 x’,然后使用语言模型对未填充信息进行概率填充以获得最终字符串 x^,从中可以导出最终输出 y。这个框架强大且有吸引力的原因有很多:它允许语言模型在大量原始文本上进行预训练,并且通过定义一个新的 Prompt 函数,模型能够执行少样本甚至零样本学习,适应很少或没有标注数据的新场景。

背景介绍

NLP 范式简史:

  • 2011-2013 年之前,主要以特征工程+有监督机器学习为主。
  • 2011-2013 年,随着神经网络在 NLP 领域的突破(Embedding),NLP 开始进入架构工程,好的架构可以学到更好的特征。
  • 2017-2019 年,转向预训练+微调范式,进入目标工程,重点在于如何设计预训练和微调阶段的目标函数。
  • 2021 年开始,预训练+Prompt+预测成为新宠,在这种范式中,不是通过目标工程使预先训练的 LM 适应下游任务,而是重新制定下游任务,使其看起来更像是在 Prompt 的帮助下在原始 LM 训练期间解决的任务。

Prompt:

  • 选择合适的 Prompt 可以操纵模型行为,使得预训练的 LM 能够直接预测要求的输出,有时甚至不需要额外的特定任务的训练。
  • 最大的优点是,给定一套合适的 Prompt 方案,以无监督方式训练的 LM 可用于解决大量任务。
  • 最大的问题是,引入了 Prompt 工程——找到合适的 Prompt 方案来让 LM 解决任务。

正式描述

有监督的深度学习一般需要大量数据,Prompt 方法试图通过学习一个 LM 来规避这个问题,该 LM 对文本 x 本身的概率 P (x; θ) 进行建模并使用该概率来预测 y,从而减少或消除了大量标注数据的需要。具体来说,基本的 Prompt 分为三步。

第一步:添加提示

这一步主要是使用一个 prompt 函数将输入的 x 修改为提示 x’,prompt 函数包括两个步骤:

  • 应用一个模板,它是一个文本字符串,有两个槽位:输入 x 的「输入槽位 [X]」 和中间生成的回答文本 z 的「回答槽位 [Z]」,稍后将映射到 y。
  • 用输入文本 x 填充槽位 [X]。

需要注意的几点:

  • 中间填充一个槽位的 Prompt 是完形填空 Prompt(上表第一行例子),输入文本完全在 z 之前的 Prompt 是前缀 Prompt(上表最后一行例子)。
  • 很多时候,模板词并不一定是自然语言,也可以是虚拟 Token,甚至连续向量。
  • [X][Z] 槽位数量可以根据任务需要灵活调整。

第二步:搜索回答

这一步主要是搜索使 LM 得分最大化的最高得分文本 zˆ。

  • 首先定义一组允许的 z,生成任务可以是任意文本,分类任务可以是一组单词。
  • 接下来定义一个函数 f_fill(x', z) 用潜在回答 z 填充提示 x’ 中的位置 [Z],得到的结果一般被称为 filled prompt,如果填充的是正确回答,则被称为 answered prompt
  • 最后,通过使用预训练的 LM 计算相应填充 Prompt 的概率来搜索潜在回答集 z。

第三步:映射回答

最后,我们希望从得分最高的回答 zˆ 到得分最高的输出 yˆ。这在 answer 本身就是 output(文本生成)时并不重要,但是有时候多个 answer 可以映射成同一个输出(比如 excellent、fabulous、wonderful 等可以表示为一个单独的类型:++)。

Prompt 设计注意事项

  • 预训练模型的选择
  • Prompt 工程
  • 回答工程
  • 扩展范式
  • 基于 Prompt 的训练策略

预训练模型

主要介绍各种预训练 LM 的系统视图:

  • 以更系统的方式沿各个轴组织它们
  • 特别关注 prompt 方法的显著方面

训练目标

SLM:自回归的方式,从左往右每次预测一个 Token。一个流行的变换是「去噪目标」——给输入添加一些噪声,然后根据噪声输入预测原始输入。

  • CTR(Corrupted Text Reconstruction):对输入句子的噪声部分计算 loss,将其恢复到其未损坏的状态
  • FTR(Full Text Reconstruction):计算整个输入文本的损失来重建文本,无论其是否有噪声

不同的训练目标在 Prompt 方面也有侧重,比如自回归的 LM 可能更适合前缀 Prompt,重建目标可能更适合完形填空 Prompt。另外,LM 和 FTR 目标可能更适合文本生成,而分类可使用任意目标。

噪声函数

特定类型,先验知识(如实体)等都可以作为噪声类型,比如:

  • Masking:值得说明的是,mask 可以来自某个随机分布,也可以特殊设计以引入先验知识。
  • Replacement:和 mask 类似,但不是用 [mask] token 替换,而是其他 token 或信息。
  • Deletion:这个操作经常和 FTR 损失一起使用。
  • Permutation:文本首先被切成不同的 span,然后重新排列成新文本。

表征方向

主要有两种计算方式:

  • Left-to-Right:用在标准 LM 或 FTR 的输出端。
  • Bidirectional

目前一般使用 mask 策略将二者合并,在 Transformer 架构中,主要使用 attention mask。

典型预训练方法

  • 从左到右语言模型:auto-regressive LM 的一种;一般太大不太好预训练和微调。
  • Masked 语言模型:一般更适合 NLU 或分析类任务(分类、推理、抽取式 QA 等)。
  • Prefix 和 Encoder-Decoder:
    • Prefix:基于一个前缀序列 x 解码 y,x 使用相同的参数。为了更好地学习到 x 的表征,文本重建目标经常被同时使用。
    • Encoder-Decoder:基于一个分离的 Encoder 编码 x,Encoder 和 Decoder 的参数不共享,和 Prefix 一样,噪声也会被引入以对 x 更好地建模。
    • 可以用在文本生成任务中,也可以使用 prompt,不过最新的研究表明,其他非生成任务,例如信息提取、问和文本生成评估可以 通过提供适当的 prompt 来重新表述生成问题。
    • 因此 prompt 方法拓宽了生成式任务预训练模型的适用性,并且打破了不同任务之间统一建模的难度。

Prompt工程

主要探讨如何创建 prompt 函数能够对下游任务最有效。必须先考虑 prompt 形状,然后再决定采用手动或自动方法来创建。

Prompt形状

两种不同的 prompt:完型填空和前缀。后者一般用于标准的 auto-regressive LM,前者主要是和 masked LM。全文本重建模型可以使用完型填空或前缀。对一些多输入的任务,prompt 模板必须也包含多个输入。

人工Prompt工程

创建 Prompt 的最自然方法是基于人类内省手动创建直观的模板。

自动模板学习

人工的问题:

  • 是个艺术活儿,尤其是复杂任务(如语义解析)。
  • 再有经验也不一定能找到最优的 prompt。

自动方法可以分成两种:

  • 离散的:prompt 是实际文本。
  • 连续的:prompt 在 LM 的 embedding 空间。

从另一个角度看:

  • 静态的:每个输入使用相同的 prompt。
  • 动态的:每个输入都有自定义的模板。

离散Prompt

  • Prompt 挖掘:在大规模文本中找同时包含输入 x 和标签 y 的语料,找到输入和输出的中心词或依赖路径,高频的词或路径可以作为模板,如:[X] middle words [Z]
  • Prompt 释义:采用种子 prompt,将其释义为一组候选 prompt,然后选择在目标任务上 acc 最高的。
  • 基于梯度搜索:采用梯度搜索找到可以触发基础预训练 LM 以生成所需目标预测的短序列。
  • Prompt 生成:当做文本生成任务 “搜索” 模板 Token。
  • Prompt 评分:先人工弄一些模板作为候选,然后填充输入和回答槽位以形成 prompt,然后使用 LM 对填充的 prompt 进行评分,选择 LM 概率最高的 prompt。

连续Prompt

因为提示 prompt 的目的是找到一种允许 LM 有效执行任务的方法,而不是供人类消费,所以没有必要将其限制为人类可解释的自然语言。直接在模型的 embedding 空间执行 prompted 去除了两个限制:

  • 放宽了 embedding 必须是自然语言的词语的约束。
  • 取消模板由预训练 LM 的参数参数化的限制,模板可以有自己的参数。

代表性的方法包括:

  • Prefix 微调:将一系列连续的特定于任务的向量添加到输入的方法,同时保持 LM 参数不变。
  • 用离散 Prompt 初始化后微调:
  • Hard-Soft Prompt 超参微调:不同于直接学习 prompt 模板,而是将可训练的变量插入到输入的 embedding中来学习连续 prompt。

这一类方法其实是假设输入和标签之间有那么一个 prompt,然后在模型参数中去加入 prompt 参数。

Answer工程

Prompt 工程主要设计输入,Answer 工程用来搜索回答空间,然后映射到原始的输出上。

Answer 形状

  • Token:预训练模型词表(或它的子集)中的某个 Token。
  • Span:常和完形填空 prompt 一起用。
  • Sentence:常和前缀 prompt 一起用。

实际使用时要看任务,Token 和 Span 常用在分类、关系抽取、NER 等;Sentence 常用在生成、多选 QA 等。

Answer空间设计方法

  • 人工设计
    • 无限制空间:回答空间就是所有 Token;这种情况最好将回答 z 直接映射到标签 y。
    • 有限制空间:分类、NER、多选 QA 等,可以设计一些主题相关的标签。
  • 离散回答搜索
    • Answer 释义:使用释义扩展回答空间。
    • 修剪再搜索:先生成一个几个合理回答的初始修剪回答空间,然后进一步搜索修剪空间选择最终回答集。
    • 标签分解:在关系抽取任务中,将关系标签分解成构成的词然后用作回答。
  • 连续回答搜索
    • 很少有研究探索使用 soft answer token(可以通过梯度下降优化)的可能性。比如为每个标签分配一个虚拟 Token 并优化其 embedding。

Multi-Prompt学习

Prompt 集成

推理时使用多个未回答的 prompt 进行输入的过程预测。

  • 简单平均:对不同 prompt 的概率取平均值。
  • 加权平均:权重一般是基于表现预先设置好的,或者使用训练数据优化得到。
  • 投票:多数为主。
  • 知识蒸馏:多个深度学习模型可以蒸馏到一个模型中。
  • 文本生成的 Prompt 集成:使用标准方法,基于回答序列下个词的集成概率生成输出。

Prompt 增强

提示增强,有时也称为演示学习,提供了一些额外的回答 prompt,可用于演示 LM 应如何为使用输入 x 实例化的实际 prompt 提供回答。

  • Sample 选择:few-shot 场景下,不同样本的选择会有非常不同的结果。可以选择和输入句子在嵌入空间中距离最接近的。
  • Sample 排序:不同的顺序也对模型性能有不同影响,可以用一些方法选择得分最高的排列。

增强方法与召回方法相关——提供更多的上下文来提升效果。

Prompt 合成

使用多个 “子 Prompt”,每个子任务一个,然后在此基础上定义 “合成 Prompt”。

Prompt 分解

一个样本多个预测值的任务,可以将全部 prompt 分成多个不同的 “子 Prompt”,每个回答一个 prompt。

训练策略

介绍如何获取适当的 prompt 和相应的回答。

训练设置

  • Zero-Shot:无需对 LM 进行任何明确的下游任务训练即可使用。具体的,简单使用 LM 预测文本概率,并按原样应用它来填充为指定任务而定义的完形填空或前缀。
  • Full-Data 学习:使用大量数据训练。
  • Few-Shot 学习:使用少量数据训练。

参数更新方法

共有五种微调策略:

方法 优势 劣势
Promptless Fine-tuning 1. 简单,不需要设计prompt;
2. 微调所有参数允许模型适应大规模数据。
1. LM 在较小的数据集上可能过拟合或无法稳定学习。
Tuning-free Prompting 1. 效率高,没有参数更新;
2. 没有灾难性遗忘;
3. 可用于 zero-shot。
1. 高 acc 需要大量 prompt 工程;
2. 在 in-context learning 中,提供多个回答 prompt 在推理时会比较慢,所以难以使用大规模训练数据。
Fixed-LM Prompt Tuning 1. 可以保持 LM 的知识;
2. 适用于 few-shot;
3. 比上一个效果好。
1. 不适用于 zero-shot 场景;
2. few-shot 场景下有效的同时,在大规模数据下表征受限;
3. 通过选择超参数或种子 prompt 进行 Prompt 工程是必要的;
4. Prompt 通常不是人类可解释或可操作的。
Fixed-prompt LM Tuning 1. Prompt 或 Answer 工程更完整地指定任务,能够更有效地学习,特别是在 few-shot 场景中。 1. Prompt 或 Answer 工程依然需要;
2. 在一个下游任务微调的 LM 在另一个下可能无效。
Prompt+LM Tuning 1. 最具表现力的方法,可能适用于高数据设置。 1. 需要训练和存储所有参数;
2. 在小数据集上可能过拟合。
  • 不使用 Prompt 微调:标准的微调。
  • 不微调 Prompt:基于固定的预训练参数和 prompt 生成回答。不微调的 prompting 和 prompt 增强组合也被称为 in-context learning。
  • 固定预训练模型微调 Prompt:Prompt 相关参数引入,并使用下游任务训练数据的有监督信号更新。
  • 固定 Prompt 微调预训练模型:标准的微调+固定参数的 prompt,在 few-shot 场景下特别有效。最自然的方法是提供一个离散的文本模板,应用于每个训练和测试样本。Answer 工程+部分 LM 微调可以减少 Prompt 工程,比如顶一个非常简单的模板:null prompt,输入和 mask 直接连在一起:[X][Z],没有任何模板词,结果效果还可以。
  • 预训练模型+Prompt同时微调:Prompt 参数和全部(或部分)预训练模型参数一起更新。

应用

知识探索

  • 事实探索:预训练模型参数固定,知识通过将原始输入转为完形填空 prompt 来召回。Prompt 可以人工制作或自动发现。
  • 语言探索:预训练模型处理语言现象。

分类任务

Prompting 分类任务的关键是将其重新表述为适当的 Prompt。比如 prompt:the topic of this document is [Z],会被丢入预训练模型用来填空。

  • 文本分类:使用完形填空 Prompt,大多数研究聚焦在少样本学习+ 固定 prompt 微调 LM 策略。
  • 自然语言推理:使用完形填空 Prompt,研究主要集中在少样本学习设置中的模板搜索,答案空间 Z 通常是从词汇表中手动预选的。

信息抽取

  • 关系抽取,相比分类的两个挑战:
    • Label 空间大:采用适配的答案选择方法。
    • 不同的 Token 可能很重要(如实体)或不重要:采用目标导向的 prompt 模板构建。
  • 语义解析,做法:
    • 当做释义任务。
    • 限制 decode 时只输出语法有效的。
  • 命名实体识别
    • 难在:每个 unit 要预测为一个 Token 或 Span;Token 标签之间有潜在的关系。
    • 枚举文本 Span,在人工模板中,考虑每种实体类型的生成概率。

推理

  • 常识推理:完形填空或评估每个候选的生成概率。
  • 数学推理:只能做简单的操作。

问答

抽取 QA、多选 QA、自由 QA。不同格式的 QA 任务可以使用同一个框架解决。

文本生成

前缀 Prompt + 自回归预训练模型。

文本生成的自动评估

将生成文本的评估概念化为文本生成问题,使用预训练的序列到序列建模,然后使用 prefix prompt 使评估任务更接近预训练任务。

多模态学习

将每个图片表征为一个序列的连续 embedding,一个固定参数的预训练 LM 使用这个 prefix 生成文本(如图片说明)。

Meta 应用

  • 领域适配:使用自生成的领域相关特征来增强原始文本输入,并使用 seq2seq 预训练模型将序列标记作为序列到序列问题。
  • 纠偏:先计算给定输入文本下个词的概率,然后计算原始文本附加上自我诊断的文本后下个词的概率,这两个概率可以组合来压制不想要特性(偏见)。比如类似 “The following text contains violence. [X][Z] 模板,X 是输入文本,Z 是 Yes/No。
  • 数据集构建:给定确定的说明生成语料。比如相似句的模板 Write two sentences that mean the same thing. [X][Z],尝试生成一个和输入句子共享相同语义的句子。

资源

  • 数据集

  • Prompts

相关主题

主要介绍 Prompt 在这些主题下是咋样的。

  • 集成学习:选择多个不同的 prompt 模板,不需要训练多次。
  • 少样本学习:即使没有任何参数调整,Prompt 增强直接将几个标注样本添加到当前处理的样本中,从预训练的 LM 中获取知识。
  • 更大上下文学习:Prompt 增强可以看成在输入中增加标签相关的样本。
  • 搜索改写:
    • 相同点:目的是通过问一个正确的问题更好地使用已有知识;知识是个黑盒子,研究人员必须学习如何仅基于问题以最佳方式探索它。
    • 不同点:知识库(搜索引擎或QA系统 VS LM);Prompt 改变了任务的形式。
  • 基于 QA 的任务改写:都是使用问题来指定任务,但 Prompt 的关键是如何更好地利用预训练 LM 中的知识。
  • 受控生成:
    • 相同点:为了更好地生成,都给输入文本添加了额外信息;如果可控生成是基于 seq2seq 的预训练模型(如 BART),就可以被看作使用依赖输入的 prompt 和 prompt+LM fine-tuning 策略的 Prompt 学习。
    • 不同点:在受控生成中,控制通常在生成的风格或内容上执行,不一定需要预训练模型,文本生成中 Prompt 的主要动机是指定任务本身并利用好预训练模型;文本生成 Prompt 学习大多共享一个数据集或任务级别的 Prompt,很少有探索依赖输入的,但这在受控生成中是常见的配置,且很有效。
  • 有监督注意力:Prompt 学习和监督注意力都旨在提取具有一些线索的重要信息,这些线索需要单独提供。 为了解决这个问题,监督注意力方法尝试使用额外的损失函数来学习预测人工标注语料库上的 gold 注意力。
  • 数据增强:添加 prompts 可以实现与跨分类任务平均添加 100 个数据点类似的准确度改进。

挑战

Prompt 设计

  • 超越分类和生成任务:信息提取和文本分析讨论的比较少,主要是因为设计 Prompt 不直观。
  • 用结构化信息 Prompt:树、图、表或关系结构在 Prompt 或 Answer 中如何更好地表示。
  • 模板与答案的纠缠:如何同时搜索或学习模板和回答的最佳组合。

Answer 工程

  • 多种类和长回答分类任务:类型特别多时,如何选择合适的回答空间;使用多 Token 回答时,如何更好地使用 LM decode 多 Token。
  • 生成任务的多回答:如何使用语法多样但语义一致的多个回答引导学习过程。

微调策略选择

在研究开始阶段,缺乏对多种方法之间权衡的系统理解。

多 Prompt 学习

  • 集成:蒸馏多个 prompts 的知识,文本生成任务用的很少(相对复杂)。
  • 组合和分解:如何做出最佳选择。
  • 增强:现有方法受限于输入长度,如何选择有用的并按照合适的顺序排列。
  • 共享:多任务、领域或语言。如何设计单个针对不同任务的 prompt,如何调整它们之间的交互。见下图。

预训练模型选择

如何选择它们以更好地利用基于 Prompt 的学习。

理论和实证分析

非常罕见。目前有:soft-prompt 有助于提取特定任务信息;文本分类任务可以改写为句子完成任务;分类任务中,Prompt 通常平均价值 100 个数据点。

可迁移性

在微调的小样本学习场景下选择的 prompts 在相似大小的模型中可以很好地泛化,但在真正小样本学习场景下泛化却不像刚刚那样有效。在两种场景下,模型大小很不同时迁移效果较差。

不同范式组合

目前主要建立在预训练+微调范式开发的预训练模型之上,预训练方法是否对 Prompt 也有效;是否可以重新考虑预训练方法。

Prompting 方法较准

当使用预训练模型生成概率预测回答时,概率分布没有很好地校准(比如有多数标签偏差、最近标签偏差和常见 Token 偏差)。即便有一个校准概率分布,当一个输入一个回答时也需要小心,因为同义的高频词会有更高的概率。要解决该问题,只能:执行 Answer 工程使用释义方法构建一个综合的 gold answer 集合;基于上下文内的先验可能性校准词概率。