NLP之ELECTRA:ELECTRA的简介、安装和使用方法、案例应用之详细攻略
目录
《ELECTRA: Pre-training Text Encoders as Discriminators Rather Than Generators》翻译与解读
相关论文
《ELECTRA: Pre-training Text Encoders as Discriminators Rather Than Generators》翻译与解读
地址 | |
时间 | 2020年3月23日 |
作者 | Kevin Clark, Minh-Thang Luong, Quoc V. Le, Christopher D. Manning Stanford和Google |
总结 | 该论文提出的ELECTRA模型目的是解决现有语言模型(如BERT)预训练任务的效率问题。 背景痛点:现有语言模型如BERT使用masked language modeling(MLM)预训练策略,即将输入文本中的部分词汇替换为[MASK]标签,再训练模型还原原词。这种策略训练效率较低。 解决方案:ELECTRA模型采用替换预测检测(replaced token detection)这个新的预训练任务。任务是利用生成器网络对部分输入词汇进行替换,形成损坏文本,然后训练鉴别器网络预测原始词汇是否被替换。 核心特征: >> 与MLM不同,该任务通过对所有词汇进行预测,而不是仅对少量词汇的还原,更高效。 >> 鉴别器网络学习到的上下文表示能力比生成网络更强,从而在相同规模与计算资源下效果更好。 优势: >> 在相同计算资源下,ELECTRA模型能够超越采用MLM预训练的比特等大模型,表现出色。 >> 小模型训练只需4天,在GLUE语言理解任务上超越需30倍计算资源的 GPT 模型。 >> 大规模训练后也能和RoBERTa/XLNet等top模型相比,在相同计算下有更好表现。 总之,ELECTRA模型采用了一种新的替换预测检测预训练任务,利用鉴别器网络学习语义表示,从而提高预训练效率,获得优异的下游任务表现。 |
Abstract
Masked language modeling (MLM) pre-training methods such as BERT corrupt the input by replacing some tokens with [MASK] and then train a model to re-construct the original tokens. While they produce good results when transferred to downstream NLP tasks, they generally require large amounts of compute to be effective. As an alternative, we propose a more sample-efficient pre-training task called replaced token detection. Instead of masking the input, our approach cor-rupts it by replacing some tokens with plausible alternatives sampled from a small generator network. Then, instead of training a model that predicts the original identities of the corrupted tokens, we train a discriminative model that predicts whether each token in the corrupted input was replaced by a generator sample or not. Thorough experiments demonstrate this new pre-training task is more ef-ficient than MLM because the task is defined over all input tokens rather than just the small subset that was masked out. As a result, the contextual representa-tions learned by our approach substantially outperform the ones learned by BERT given the same model size, data, and compute. The gains are particularly strong for small models; for example, we train a model on one GPU for 4 days that outperforms GPT (trained using 30x more compute) on the GLUE natural lan-guage understanding benchmark. Our approach also works well at scale, where it performs comparably to RoBERTa and XLNet while using less than 1/4 of their compute and outperforms them when using the same amount of compute. | 遮蔽语言建模(MLM)预训练方法,如BERT,通过用[MASK]替换一些标记来损坏输入,然后训练模型重新构建原始标记。尽管它们在转移到下游自然语言处理(NLP)任务时产生良好的结果,但通常需要大量计算资源才能有效。作为替代方案,我们提出了一种更有效的样本预训练任务,称为替代标记检测。我们的方法不是屏蔽输入,而是用从小型生成器网络中采样的合理替代方案替换一些标记,从而破坏输入。然后,我们不是训练一个预测损坏标记的原始身份的模型,而是训练一个判别模型,来预测损坏输入中的每个标记是否被生成器样本替换。通过彻底的实验证明,与MLM相比,这个新的预训练任务更加高效,因为该任务定义在所有输入标记上,而不仅仅是被屏蔽的小子集。因此,我们的方法学习到的上下文表示远远优于在相同模型大小、数据和计算资源的情况下由BERT学到的上下文表示。这些收益在小型模型上尤为显著;例如,我们在一个GPU上训练一个模型4天,性能超过了使用30倍计算资源训练的GPT在GLUE自然语言理解基准测试上的表现。我们的方法在规模上也表现良好,在使用不到他们1/4的计算资源的情况下,性能与RoBERTa和XLNet相当,并在使用相同计算资源的情况下超越它们。 |
5 CONCLUSION
We have proposed replaced token detection, a new self-supervised task for language representation learning. The key idea is training a text encoder to distinguish input tokens from high-quality nega-tive samples produced by an small generator network. Compared to masked language modeling, our pre-training objective is more compute-efficient and results in better performance on downstream tasks. It works well even when using relatively small amounts of compute, which we hope will make developing and applying pre-trained text encoders more accessible to researchers and practi-tioners with less access to computing resources. We also hope more future work on NLP pre-training will consider efficiency as well as absolute performance, and follow our effort in reporting compute usage and parameter counts along with evaluation metrics. | 我们提出了替代标记检测,这是一种新的自监督任务,用于语言表示学习。关键思想是训练一个文本编码器来区分输入令牌和由小型生成器网络产生的高质量负样本。与遮蔽语言建模相比,我们的预训练目标计算效率更高,并且在下游任务上的性能更好。即使在使用相对较小的计算资源时也能很好地工作,我们希望这将使开发和应用预训练文本编码器对于研究人员和实践者更加可访问。我们还希望未来在NLP预训练上的更多工作会考虑效率以及绝对性能,并跟随我们在报告计算使用和参数计数以及评估指标方面的努力。 |
ELECTRA的简介
ELECTRA是一种用于自监督语言表示学习的方法。它可以用相对较少的计算资源预训练Transformer网络。ELECTRA模型被训练以区分由另一个神经网络生成的“真实”输入标记与“伪造”输入标记,类似于GAN的判别器。在小规模上,即使在单个GPU上训练,ELECTRA也能取得强大的结果。在大规模上,ELECTRA在SQuAD 2.0数据集上取得了最先进的结果。
有关详细描述和实验结果,请参阅我们的ICLR 2020论文《ELECTRA: 将文本编码器预训练为判别器而非生成器》。
该存储库包含用于预训练ELECTRA的代码,包括在单个GPU上的小型ELECTRA模型。它还支持在下游任务上对ELECTRA进行微调,包括分类任务(例如,GLUE),问答任务(例如,SQuAD)和序列标记任务(例如,文本分块)。
该存储库还包含Electric的代码,这是ELECTRA的一种受能量模型启发的版本。Electric提供了ELECTRA作为“负采样”填空模型的更为原则性的视角。它还可以高效地为文本生成伪似然分数,这可以用于重新排序语音识别或机器翻译系统的输出。有关Electric的详细信息,请参阅我们的EMNLP 2020论文《将Transformer预训练为基于能量的填空模型》。
1、发布的模型
我们最初发布了三个预训练模型:
Model | Layers | Hidden Size | Params | GLUE score (test set) | Download |
---|---|---|---|---|---|
ELECTRA-Small | 12 | 256 | 14M | 77.4 | link |
ELECTRA-Base | 12 | 768 | 110M | 82.7 | link |
ELECTRA-Large | 24 | 1024 | 335M | 85.2 | link |
这些模型是在英语文本上进行的。它们对应于我们论文中的ELECTRA-Small++、ELECTRA-Base++、ELECTRA-1.75M。我们希望未来发布其他模型,比如多语言模型。
在GLUE上,ELECTRA-Large的得分略高于ALBERT/XLNET,ELECTRA-Base的得分高于BERT-Large,而ELECTRA-Small的得分略低于TinyBERT(但不使用蒸馏)。请参见下面的期望结果部分,以获取详细的性能数据。
ELECTRA的安装和使用方法
1、安装要求
Python 3
TensorFlow 1.15(尽管我们希望在将来支持TensorFlow 2.0)
NumPy
scikit-learn和SciPy(用于计算一些评估指标)。
2、预训练
创建一个预训练数据集 | 使用build_pretraining_dataset.py从原始文本的转储中创建一个预训练数据集。它具有以下参数: --corpus-dir:包含原始文本文件的目录,将其转换为ELECTRA示例。一个文本文件可以包含多个由空行分隔的文档。 --vocab-file:定义词块词汇表的文件。 --output-dir:将ELECTRA示例写入的位置。 --max-seq-length:每个示例的令牌数(默认为128)。 --num-processes:如果>1,可以在多个进程之间并行化处理(默认为1)。 --blanks-separate-docs:空行是否表示文档边界(默认为True)。 --do-lower-case/--no-lower-case:是否将输入文本转换为小写(默认为True)。 |
预训练 | 使用run_pretraining.py对ELECTRA模型进行预训练。它具有以下参数: --data-dir:存储预训练数据、模型权重等的目录。默认情况下,训练从<data-dir>/pretrain_tfrecords加载示例,并从<data-dir>/vocab.txt加载词汇表。 --model-name:正在训练的模型的名称。模型权重将默认保存在<data-dir>/models/<model-name>中。 --hparams(可选):包含模型超参数、数据路径等的JSON字典或JSON文件的路径。有关支持的超参数,请参见configure_pretraining.py。 如果训练中断,重新运行带有相同参数的run_pretraining.py将从中断的地方继续训练。 |
继续预训练 | 您可以从已发布的ELECTRA检查点继续预训练 将model-name设置为指向下载的模型的名称(例如,如果您将权重下载到$DATA_DIR/electra_small,则--model-name electra_small)。 通过在--hparams中添加“num_train_steps”: 4010000(例如)来设置num_train_steps。这将继续对小型模型进行10000步的训练(已经进行了400万步的训练)。 增加学习率以考虑线性学习率衰减。例如,要从学习率为2e-4开始,您应该将learning_rate hparam设置为2e-4 *(400万 + 10000)/ 10000。 对于ELECTRA-Small,您还需要在hparams中指定“generator_hidden_size”: 1.0,因为我们没有为该模型使用小型生成器。 |
3、快速入门:预训练一个小型ELECTRA模型
简介 | 这些说明将预训练一个小型ELECTRA模型(12层,256隐藏大小)。不幸的是,我们在论文中使用的数据并未公开,因此我们将使用由Aaron Gokaslan和Vanya Cohen发布的OpenWebTextCorpus代替。完全训练的模型(在v100 GPU上约4天)在GLUE性能方面大致介于GPT和BERT-Base之间。默认情况下,该模型是在长度为128的序列上进行训练的,因此不适用于运行问答。 |
设置 | 在$DATA_DIR/vocab.txt中放置一个词汇文件。我们的ELECTRA模型都使用与英语无大小写的BERT完全相同的词汇表,您可以在此处下载。 下载OpenWebText语料库(12G)并提取它(即运行tar xf openwebtext.tar.xz)。将其放置在$DATA_DIR/openwebtext中。 运行python3 build_openwebtext_pretraining_dataset.py --data-dir $DATA_DIR --num-processes 5。它将对数据进行预处理/标记化,并将示例输出为$DATA_DIR/pretrain_tfrecords下的tfrecord文件。tfrecords需要约30G的磁盘空间。 |
预训练模型
预训练模型 | 运行python3 run_pretraining.py --data-dir $DATA_DIR --model-name electra_small_owt以在数据上对小型ELECTRA模型进行100万步的训练。在Tesla V100 GPU上,这需要略微超过4天的时间。然而,该模型在200k步(在v100 GPU上训练了10小时)后应该获得不错的结果。 要定制培训,将--hparams '{"hparam1": value1, "hparam2": value2, ...}'添加到运行命令中。--hparams也可以是包含超参数的.json文件的路径。一些特别有用的选项: "debug": true对少量步数进行微调的微小ELECTRA模型。 "model_size": "small"、"base"或"large"之一:确定模型的大小 "electra_objective": false使用屏蔽语言建模而不是替代标记检测(基本上是具有动态屏蔽且没有下一个句子预测的BERT)训练模型。 "num_train_steps": n控制模型的预训练时间。 "pretrain_tfrecords": <paths>确定预训练数据的位置。请注意,您需要指定特定文件而不仅仅是目录(例如,<data-dir>/pretrain_tf_records/pretrain_data.tfrecord*) "vocab_file": <path>和"vocab_size": n可用于设置自定义wordpiece词汇表。 "learning_rate": lr,"train_batch_size": n等可用于更改训练超参数 "model_hparam_overrides": {"hidden_size": n, "num_hidden_layers": m}等可用于更改底层Transformer的超参数("model_size"标志设置默认值)。 有关支持的所有超参数,请参见configure_pretraining.py。 |
评估预训练模型
评估预训练模型 | 要在下游任务上评估模型,请参见下面的微调说明。要在openwebtext数据上评估生成器/判别器,请运行python3 run_pretraining.py --data-dir $DATA_DIR --model-name electra_small_owt --hparams '{"do_train": false, "do_eval": true}'。这将打印生成器和判别器的准确性等评估指标,并将指标写入data-dir/model-name/results。 |
微调
微调 | 使用run_finetuning.py对下游NLP任务上的ELECTRA模型进行微调和评估。它期望三个参数: --data-dir:存储数据、模型权重等的目录。默认情况下,该脚本从<data-dir>/finetuning_data/<task-name>加载微调数据,并从<data-dir>/vocab.txt加载词汇表。 --model-name:预训练模型的名称:预训练权重应存在于data-dir/models/model-name中。 --hparams:包含模型超参数、数据路径等的JSON字典(例如,--hparams '{"task_names": ["rte"], "model_size": "base", "learning_rate": 1e-4, ...}')。有关支持的超参数,请参见configure_pretraining.py。它也可以是包含超参数的.json文件的路径。您必须指定"task_names"和"model_size"(请参见下面的示例)。 评估指标将保存在data-dir/model-name/results中,默认情况下,模型权重将保存在data-dir/model-name/finetuning_models中。默认情况下,在dev集上进行评估。要定制培训,将--hparams '{"hparam1": value1, "hparam2": value2, ...}'添加到运行命令中。一些特别有用的选项: "debug": true对少量步数进行微调的微小ELECTRA模型。 "task_names": ["task_name"]:指定要训练的任务。由于代码库名义上支持多任务学习(尽管请注意这尚未经过充分测试)。 "model_size": "small"、"base"或"large"之一:确定模型的大小;必须将其设置为预训练模型的大小。 "do_train"和"do_eval":训练和/或评估模型(默认情况下都设置为true)。要使用“do_eval”: true并且“do_train”: false,请指定init_checkpoint,例如,python3 run_finetuning.py --data-dir $DATA_DIR --model-name electra_base --hparams '{"model_size": "base", "task_names": ["mnli"], "do_train": false, "do_eval": true, "init_checkpoint": "<data-dir>/models/electra_base/finetuning_models/mnli_model_1"}' "num_trials": n:如果>1,则使用不同的随机种子进行多次微调/评估运行。 "learning_rate": lr,"train_batch_size": n等可用于更改训练超参数。 "model_hparam_overrides": {"hidden_size": n, "num_hidden_layers": m}等可用于更改底层Transformer的超参数("model_size"标志设置默认值)。 |
设置 | 通过训练自己的ELECTRA模型(请参阅上述的预训练说明),或者下载发布的ELECTRA权重并解压缩到$DATA_DIR/models目录下(例如,如果使用大模型,则应该有一个目录$DATA_DIR/models/electra_large)来获取预训练的ELECTRA模型。 |
在GLUE任务上微调ELECTRA
在GLUE任务上微调ELECTRA | 在GLUE任务上微调ELECTRA 通过运行此脚本下载GLUE数据。通过运行mv CoLA cola && mv MNLI mnli && mv MRPC mrpc && mv QNLI qnli && mv QQP qqp && mv RTE rte && mv SST-2 sst && mv STS-B sts && mv diagnostic/diagnostic.tsv mnli && mkdir -p $DATA_DIR/finetuning_data && mv * $DATA_DIR/finetuning_data来设置数据。 然后运行run_finetuning.py。例如,要在MNLI上微调ELECTRA-Base: python3 run_finetuning.py --data-dir $DATA_DIR --model-name electra_base --hparams '{"model_size": "base", "task_names": ["mnli"]}' 或者微调使用上述说明预训练的小模型在CoLA上: python3 run_finetuning.py --data-dir $DATA_DIR --model-name electra_small_owt --hparams '{"model_size": "small", "task_names": ["cola"]}' 在问答任务上微调ELECTRA 该代码支持SQuAD 1.1和2.0,以及2019年MRQA共享任务的数据集。 SQuAD 1.1:下载训练和开发数据集,并将其移动到$DATA_DIR/finetuning_data/squadv1/(train|dev).json下。 SQuAD 2.0:从SQuAD网站下载数据集,并将其移动到$DATA_DIR/finetuning_data/squad/(train|dev).json下。 MRQA任务:从这里下载数据。将数据移动到$DATA_DIR/finetuning_data/(newsqa|naturalqs|triviaqa|searchqa)/(train|dev).jsonl。 然后运行(例如): python3 run_finetuning.py --data-dir $DATA_DIR --model-name electra_base --hparams '{"model_size": "base", "task_names": ["squad"]}' 该存储库使用SQuAD作者发布的官方评估代码和MRQA共享任务来计算指标。 |
在序列标注上微调ELECTRA
在序列标注上微调ELECTRA | 在序列标注上微调ELECTRA 从这里下载CoNLL-2000文本分块数据集,并将其放置在$DATA_DIR/finetuning_data/chunk/(train|dev).txt下。然后运行 python3 run_finetuning.py --data-dir $DATA_DIR --model-name electra_base --hparams '{"model_size": "base", "task_names": ["chunk"]}' |
添加新任务
添加新任务 | 添加新任务 在新任务上运行的最简单方法是实现一个新的finetune.task.Task,将其添加到finetune.task_builder.py,然后像平常一样使用run_finetuning.py。对于分类/问答/序列标记,您可以继承自finetune.classification.classification_tasks.ClassificationTask、finetune.qa.qa_tasks.QATask或finetune.tagging.tagging_tasks.TaggingTask。在预处理数据时,我们使用与BERT相同的分词器。 |
4、预期结果
以下是ELECTRA在各种任务上的预期结果(对于分块的测试集,对于其他任务是开发集)。请注意,微调的方差可能会很大,因此在从相同的检查点多次微调时,某些任务的得分可能会有很大波动。下面的分数显示了在大量随机种子上的中位性能。ELECTRA-Small/Base/Large是我们发布的模型。由于在较短的时间内以及在较小的数据集上训练,ELECTRA-Small-OWT的性能略差于ELECTRA-Small。
CoLA | SST | MRPC | STS | QQP | MNLI | QNLI | RTE | SQuAD 1.1 | SQuAD 2.0 | Chunking | |
---|---|---|---|---|---|---|---|---|---|---|---|
Metrics | MCC | Acc | Acc | Spearman | Acc | Acc | Acc | Acc | EM | EM | F1 |
ELECTRA-Large | 69.1 | 96.9 | 90.8 | 92.6 | 92.4 | 90.9 | 95.0 | 88.0 | 89.7 | 88.1 | 97.2 |
ELECTRA-Base | 67.7 | 95.1 | 89.5 | 91.2 | 91.5 | 88.8 | 93.2 | 82.7 | 86.8 | 80.5 | 97.1 |
ELECTRA-Small | 57.0 | 91.2 | 88.0 | 87.5 | 89.0 | 81.3 | 88.4 | 66.7 | 75.8 | 70.1 | 96.5 |
ELECTRA-Small-OWT | 56.8 | 88.3 | 87.4 | 86.8 | 88.3 | 78.9 | 87.9 | 68.5 | -- | -- | -- |
在这里查看模型在预训练期间的损失/训练曲线。Electric
要训练Electric,请使用与ELECTRA相同的预训练脚本和命令。将"electra_objective": false和"electric_objective": true传递给超参数。我们计划很快发布预训练的Electric模型!
ELECTRA的案例应用
更新中……