SetFit:高效的无提示少样本学习

SetFit:Efficient Unsupervised Few-Shot Learning

SetFit在样本效率和噪声鲁棒性方面明显优于标准微调。

使用预训练语言模型进行小样本学习已经成为解决每个数据科学家的噩梦的有希望的解决方案:处理几乎没有标签的数据 😱。

与我们在英特尔实验室和UKP实验室的研究合作伙伴一起,Hugging Face很高兴地推出SetFit:一种用于句子转换器的小样本微调的高效框架。SetFit仅使用少量标记数据即可实现高准确率-例如,在客户评论(CR)情感数据集上,每个类别仅使用8个标记示例,SetFit与完整训练集中的RoBERTa Large进行微调时具有竞争力 🤯!

与其他小样本学习方法相比,SetFit具有几个独特的功能:

🗣 无提示或语言化器:当前的小样本微调技术需要手工制作的提示或语言化器将示例转换为适合底层语言模型的格式。SetFit通过直接从少量标记文本示例生成丰富的嵌入来完全摒弃提示。

🏎 训练速度快:SetFit不需要像T0或GPT-3这样的大规模模型即可实现高准确率。因此,它通常比训练和推理速度快一个数量级(或更多)。

🌎 多语言支持:SetFit可以与Hub上的任何句子转换器一起使用,这意味着您可以通过简单微调多语言检查点来对多种语言的文本进行分类。

有关更多详细信息,请查看我们的论文、数据和代码。在本博客文章中,我们将解释SetFit的工作原理以及如何训练您自己的模型。让我们开始吧!

它是如何工作的?

SetFit的设计考虑了效率和简洁性。SetFit首先对少量标记示例(通常每类8个或16个)进行句子转换器模型的微调。然后,对从微调的句子转换器生成的嵌入进行分类器头的训练。

SetFit的两阶段训练过程

SetFit利用句子转换器生成基于配对句子的密集嵌入的能力。在初始微调阶段,它通过对内类和外类选择创建正负对来进行对比训练。句子转换器模型然后在这些对(或三元组)上进行训练,并为每个示例生成密集向量。在第二步中,分类器头根据其对应的类别标签对编码的嵌入进行训练。在推理时,未见过的示例通过经过微调的句子转换器,生成一个嵌入,当输入到分类器头时,输出一个类别标签预测。

只需将基础句子转换器模型更换为多语言模型,SetFit就可以在多语言环境中无缝运行。在我们的实验中,SetFit在德语、日语、汉语、法语和西班牙语的分类任务中展现出有希望的结果,无论是在语言内还是跨语言设置中。

SetFit的基准测试

尽管基于比现有的小样本方法更小的模型,SetFit在各种基准测试中表现与最先进的小样本方法相当或更好。在RAFT上,使用355百万参数的SetFit RoBERTa(使用all-roberta-large-v1模型)优于PET和GPT-3。它仅略低于人类平均性能和拥有110亿参数的T-few-SetFit RoBERTa的30倍大小的模型。SetFit在11个RAFT任务中的7个上也优于人类基线。

RAFT排行榜上的突出方法(截至2022年9月)

在其他数据集上,SetFit在各种任务中显示出鲁棒性。如下图所示,仅使用每类8个示例,它通常优于PERFECT、ADAPET和微调的普通transformer。尽管无需提示且规模减小27倍,SetFit的结果也与T-Few 3B相当。

将SetFit性能与其他方法在3个分类数据集上进行比较。

快速训练和推理

比较 T-Few 3B 和 SetFit (MPNet) 在每个类别有8个标记示例的训练成本和平均性能。

由于SetFit使用相对较小的模型就能实现高准确率,因此训练速度非常快且成本更低。例如,在NVIDIA V100上使用8个标记示例对SetFit进行训练只需30秒,成本为0.025美元。相比之下,使用NVIDIA A100对T-Few 3B进行训练需要11分钟,成本约为0.7美元,相同实验的成本高出28倍。事实上,SetFit可以在像Google Colab上找到的单个GPU上运行,甚至可以在几分钟内在CPU上训练SetFit!如上图所示,SetFit的加速效果与模型性能相当。类似的加速效果也可以在推理和蒸馏SetFit模型时实现,速度提升了123倍🤯。

训练您自己的模型

为了让整个社区都能使用SetFit,我们创建了一个小型的setfit库,只需几行代码即可训练您自己的模型。首先,通过运行以下命令来安装它:

pip install setfit

接下来,我们导入SetFitModelSetFitTrainer,这是两个核心类,可以简化SetFit训练过程:

from datasets import load_dataset
from sentence_transformers.losses import CosineSimilarityLoss

from setfit import SetFitModel, SetFitTrainer

现在,让我们从Hugging Face Hub下载一个文本分类数据集。我们将使用SentEval-CR数据集,这是一个包含客户评论的数据集:

dataset = load_dataset("SetFit/SentEval-CR")

为了模拟只有少量标记示例的真实情况,我们将从训练集中每个类别中选择8个示例:

# 选择每个类别的N个示例(此处为8个)
train_ds = dataset["train"].shuffle(seed=42).select(range(8 * 2))
test_ds = dataset["test"]

现在,我们已经有了一个数据集,下一步是从Hub加载预训练的Sentence Transformer模型,并实例化一个SetFitTrainer。在这里,我们使用了paraphrase-mpnet-base-v2模型,我们发现它在许多数据集上都表现出色:

# 从Hub加载SetFit模型
model = SetFitModel.from_pretrained("sentence-transformers/paraphrase-mpnet-base-v2")

# 创建训练器
trainer = SetFitTrainer(
    model=model,
    train_dataset=train_ds,
    eval_dataset=test_ds,
    loss_class=CosineSimilarityLoss,
    batch_size=16,
    num_iterations=20, # 用于对比学习生成文本对的数量
    num_epochs=1 # 用于对比学习的轮数
)

最后一步是训练和评估模型:

# 训练和评估!
trainer.train()
metrics = trainer.evaluate()

就是这样 – 您现在已经训练了您的第一个SetFit模型!记得将训练好的模型推送到Hub上 🙂

# 将模型推送到Hub
# 确保先使用huggingface-cli login登录
trainer.push_to_hub("my-awesome-setfit-model")

虽然这个示例展示了如何使用一种特定类型的基础模型来完成,但任何Sentence Transformer模型都可以用于不同的性能和任务。例如,使用多语言的Sentence Transformer模型可以将小样本分类扩展到多语言环境。

下一步

我们已经展示了SetFit是一种有效的小样本分类方法。在接下来的几个月里,我们将探索该方法在自然语言推理和标记分类等任务上的泛化效果。同时,我们非常期待行业从业者将SetFit应用于他们的用例中 – 如果您有任何问题或反馈,请在我们的GitHub存储库上提出问题🤗。

祝您进行小样本学习愉快!