橫掃各項NLP任務的BERT模型有了PyTorch實現

2020-11-21 騰訊網

新智元報導

來源:GitHub

作者:huggingface 編譯:肖琴

【新智元導讀】谷歌NLP模型的官方TensorFlow實現很強,現在,它的PyTorch版本來了!只需簡單運行一次轉換腳本,就可得到一個PyTorch模型,且結果與原始版本相近,甚至更好。

上周,谷歌最強NLP模型BERT開源了官方TensorFlow代碼和預訓練模型,引起大量關注。

現在,PyTorch用戶的福利來了:一個名為Hugging Face的團隊近日公開了BERT模型的谷歌官方TensorFlow庫的op-for-op PyTorch重新實現:

https://github.com/huggingface/pytorch-pretrained-BERT

這個實現可以為BERT加載任何預訓練的TensorFlow checkpoint(特別是谷歌的官方預訓練模型),並提供一個轉換腳本

BERT-baseBERT-large模型的參數數量分別為110M和340M,為了獲得良好的性能,很難使用推薦的batch size在單個GPU上對其進行微調。為了幫助微調模型,這個repo還提供了3種可以在微調腳本中激活技術:梯度累積(gradient-accumulation)multi-GPU分布式訓練

其結果如下:

在序列級MRPC分類任務上,該實現使用小型BERT-base模型再現了原始實現的84%-88%的準確率。

在token級的SQuAD 任務上,該個實現使用小型BERT-base模型再現了原始實現的88.52 F1的結果。

作者表示,正致力於在其他任務以及更大的BERT模型上重現結果。

BERT模型的PyTorch實現

這個存儲庫包含了谷歌BERT模型的官方TensorFlow存儲庫的op-for-op PyTorch重新實現。谷歌的官方存儲庫是與BERT論文一起發布的:BERT: Pre-training of Deep Bidirectional Transformers for Language Understanding,作者是Jacob Devlin、Ming-Wei Chang、Kenton Lee和Kristina Toutanova。

這個實現可以為BERT加載任何預訓練的TensorFlow checkpoint(特別是谷歌的預訓練模型),並提供了一個轉換腳本(見下文)。

此外,我們將在本周晚些時候添加多語言版本和中文版本的模型代碼。

腳本:加載任何TensorFlow檢查點

使用convert_tf_checkpoint_to_pytorch.py腳本,你可以在PyTorch保存文件中轉換BERT的任何TensorFlow檢查點(尤其是谷歌發布的官方預訓練模型)。

這個腳本將TensorFlow checkpoint(以bert_model.ckpt開頭的三個文件)和相關的配置文件(bert_config.json)作為輸入,並為此配置創建PyTorch模型,從PyTorch模型的TensorFlow checkpoint加載權重並保存生成的模型在一個標準PyTorch保存文件中,可以使用 torch.load() 導入(請參閱extract_features.py,run_classifier.py和run_squad.py中的示例)。

只需要運行一次這個轉換腳本,就可以得到一個PyTorch模型。然後,你可以忽略TensorFlow checkpoint(以bert_model.ckpt開頭的三個文件),但是一定要保留配置文件(bert_config.json)和詞彙表文件(vocab.txt),因為PyTorch模型也需要這些文件。

要運行這個特定的轉換腳本,你需要安裝TensorFlow和PyTorch。該庫的其餘部分只需要PyTorch。

下面是一個預訓練的BERT-Base Uncased 模型的轉換過程示例:

exportBERT_BASE_DIR=/path/to/bert/uncased_L-12_H-768_A-12python convert_tf_checkpoint_to_pytorch.py \ --tf_checkpoint_path$BERT_BASE_DIR/bert_model.ckpt \ --bert_config_file$BERT_BASE_DIR/bert_config.json \ --pytorch_dump_path$BERT_BASE_DIR/pytorch_model.bin

你可以在這裡下載Google的預訓練轉換模型:

https://github.com/google-research/bert#pre-trained-models

BERT的PyTorch模型

在這個庫裡,我們提供了三個PyTorch模型,你可以在modeling.py中找到:

BertModel- 基本的BERT Transformer 模型

BertForSequenceClassification- 頂部帶有sequence classification head的BERT模型

BertForQuestionAnswering- 頂部帶有token classification head 的BERT模型,

以下是每類模型的一些細節。

1 . BertModel

BertModel是一個基本的BERT Transformer模型,包含一個summed token、位置和序列嵌入層,然後是一系列相同的self-attention blocks(BERT-base是12個blocks, BERT-large是24個blocks)。

輸入和輸出與TensorFlow 模型的輸入和輸出相同。

具體來說,該模型的輸入是:

input_ids:一個形狀為[batch_size, sequence_length]的torch.LongTensor,在詞彙表中包含單詞的token索引

token_type_ids:形狀[batch_size, sequence_length]的可選torch.LongTensor,在[0,1]中選擇token類型索引。類型0對應於句子A,類型1對應於句子B。

attention_mask:一個可選的torch.LongTensor,形狀為[batch_size, sequence_length],索引在[0,1]中選擇。

模型的輸出是由以下內容組成的一個元組:

all_encoder_layers:一個大小為[batch_size, sequence_length,hidden_size]的torch.FloatTensor列表,它是每個注意塊末端隱藏狀態的完整序列列表(即BERT-base的12個完整序列,BERT-large的24個完整序列)

pooled_output:一個大小為[batch_size, hidden_size]的torch.FloatTensor,它是在與輸入(CLF)的第一個字符相關聯的隱藏狀態之上預訓練的分類器的輸出,用於訓練Next-Sentence任務(參見BERT的論文)。

extract_features.py腳本提供了有關如何使用這類模型的示例,該腳本可用於為給定輸入提取模型的隱藏狀態。

2 . BertForSequenceClassification

BertForSequenceClassification是一個fine-tuning 模型,包括BertModel,以及BertModel頂部的一個序列級分類器(sequence-level classifier)。

序列級分類器是一個線性層,它將輸入序列中第一個字符的最後隱藏狀態作為輸入(參見BERT論文中的圖3a和3b)。

run_classifier.py腳本提供了關於如何使用此類模型的示例,該腳本可用於使用BERT微調單個序列(或序列對)分類器,例如用於MRPC任務。

3. BertForQuestionAnswering

BertForQuestionAnswering是一個fine-tuning 模型,包括BertModel,它在最後隱藏狀態的完整序列之上具有token級分類器(token-level classifiers)。

token-level 分類器將最後隱藏狀態的完整序列作為輸入,並為每個token計算得分,(參見BERT論文的圖3c和3d)。

run_squad.py腳本提供了有關如何使用此類模型的示例,該腳本可用於使用BERT微調token分類器,例如用於SQuAD任務。

安裝、要求、測試

這段代碼在Python 3.5+上進行了測試。必備條件是:

PyTorch (> = 0.4.1)

tqdm

安裝dependencies:

pip install -r ./requirements.txt

測試文件夾中包含一系列測試,可以使用pytest運行(如果需要,請安裝pytest: pip install pytest)。

你可以使用以下命令運行測試:

python -m pytest -sv tests/

大批量訓練:梯度積累、多GPU、分布式訓練

BERT-base和BERT-large的模型參數分別是110M和340M,為了獲得良好的性能(大多數情況下批大小是32),很難在單個GPU上對它們進行微調。

為了幫助對這些模型進行微調,我們介紹了在微調腳本run_classifier.py和run_squad中可以激活的四種技術:優化CPU、梯度積累、multi-gpu和分布式訓練。

有關如何使用這些技術的更多細節,你可以閱讀這篇關於PyTorch批量訓練技巧的文章:

https://medium.com/huggingface/training-larger-batches-practical-tips-on-1-gpu-multi-gpu-distributed-setups-ec88c3e51255

BERT的微調:運行示例

我們展示了與原始實現相同的示例:在MRPC分類語料庫上微調sequence級分類器和在問題回答數據集SQuAD上微調token級分類器。

在運行這些示例之前,應該先下載GLUE數據,並將其解壓縮到某個目錄$GLUE_DIR。還需下載BERT-Base checkpoint,將其解壓縮到某個目錄$BERT_BASE_DIR,並將其轉換為上一節所述的PyTorch版本。

這個示例代碼基於微軟研究意譯語料庫(MRPC)調優了BERT-Base,在單個K-80上運行只需不到10分鐘。

exportGLUE_DIR=/path/to/gluepython run_classifier.py \ --task_name MRPC \ --do_train \ --do_eval \ --do_lower_case \ --data_dir$GLUE_DIR/MRPC/ \ --vocab_file$BERT_BASE_DIR/vocab.txt \ --bert_config_file$BERT_BASE_DIR/bert_config.json \ --init_checkpoint$BERT_PYTORCH_DIR/pytorch_model.bin \ --max_seq_length 128 \ --train_batch_size 32 \ --learning_rate 2e-5 \ --num_train_epochs 3.0 \ --output_dir /tmp/mrpc_output/

基於原始實現的超參數進行測試,評估結果達到84%到88%。

第二個示例是基於SQuAD問題回答任務微調BERT-Base。

exportSQUAD_DIR=/path/to/SQUADpython run_squad.py \ --vocab_file$BERT_BASE_DIR/vocab.txt \ --bert_config_file$BERT_BASE_DIR/bert_config.json \ --init_checkpoint$BERT_PYTORCH_DIR/pytorch_model.bin \ --do_train \ --do_predict \ --do_lower_case --train_file$SQUAD_DIR/train-v1.1.json \ --predict_file$SQUAD_DIR/dev-v1.1.json \ --train_batch_size 12 \ --learning_rate 3e-5 \ --num_train_epochs 2.0 \ --max_seq_length 384 \ --doc_stride 128 \ --output_dir ../debug_squad/

使用之前的超參數進行訓練,得到如下結果:

{"f1": 88.52381567990474,"exact_match": 81.22043519394512}

在GPU上微調BERT-large

上面列出的選項允許在GPU上很容易地對BERT-large進行微調,而不是像原始實現那樣使用TPU。

例如,針對SQuAD任務微調BERT-large模型,可以在伺服器上用4個k-80在18個小時內完成。我們的結果與TensorFlow的實現結果相似(實際上是略高):

{"exact_match": 84.56953642384106,"f1": 91.04028647786927}

為了得到這些結果,我們使用了以下組合:

多GPU訓練(在多GPU伺服器上自動激活),

梯度累積

在CPU上執行優化步驟,將Adam的平均值存儲在RAM中。

以下是我們在此次運行中使用的超參數的完整列表:

python ./run_squad.py --vocab_file$BERT_LARGE_DIR/vocab.txt --bert_config_file$BERT_LARGE_DIR/bert_config.json --init_checkpoint$BERT_LARGE_DIR/pytorch_model.bin --do_lower_case --do_train --do_predict --train_file$SQUAD_TRAIN--predict_file$SQUAD_EVAL--learning_rate 3e-5 --num_train_epochs 2 --max_seq_length 384 --doc_stride 128 --output_dir$OUTPUT_DIR/bert_large_bsz_24 --train_batch_size 24 --gradient_accumulation_steps 2 --optimize_on_cpu

【加入社群】

新智元 AI 技術 + 產業社群招募中,歡迎對 AI 技術 + 產業落地感興趣的同學,加小助手微信號:aiera2015_3入群;通過審核後我們將邀請進群,加入社群後務必修改群備註(姓名 - 公司 - 職位;專業群審核較嚴,敬請諒解)。

相關焦點

  • 最強NLP預訓練模型!谷歌BERT橫掃11項NLP任務記錄
    BERT 是首個在大批句子層面和 token 層面任務中取得當前最優性能的基於微調的表徵模型,其性能超越許多使用任務特定架構的系統。BERT 刷新了 11 項 NLP 任務的當前最優性能記錄。本論文還報告了 BERT 的模型簡化測試(ablation study),證明該模型的雙向特性是最重要的一項新貢獻。代碼和預訓練模型將發布在 goo.gl/language/bert。
  • 劍指TensorFlow,PyTorch Hub官方模型庫一行代碼復現主流模型
    pytorch_GAN_zoo現在,我們可以看看最簡單的案例,torchvision 的 hubconf.py:在 torchvision,模型有以下幾部分:每個模型文件都可以獨立的執行這些模型不依賴 PyTorch 以外的包(在 hubconf.py 中以及集成了相關依賴:dependencies['torch'])這些模型不需要單獨的模型入口(entry-point
  • 圖解當前最強語言模型BERT:NLP是如何攻克遷移學習的?
    示例數據集:SST:https://nlp.stanford.edu/sentiment/事實檢查輸入:句子。輸出:「事實聲明」或「非事實聲明」。更雄心勃勃且更有未來感的示例:輸入:稱述句。輸出:「真」或「假」。Full Fact 是一家組織機構為公共利益構建的一款自動事實檢查工具。
  • Transformers2.0讓你三行代碼調用語言模型,兼容TF2.0和PyTorch
    項目地址:https://github.com/huggingface/transformersTransformers 2.0 新特性像 pytorch-transformers 一樣使用方便;像 Keras 一樣功能強大和簡潔;在 NLU 和 NLG 任務上實現高性能;對教育者和實踐者的使用門檻低。
  • 谷歌開源 BERT 模型原始碼
    模型以來,BERT 模型以其雙向、深層等特點,成功在 11 項 NLP 任務中取得 state of the art 的結果,贏得自然語言處理學界的一片讚譽之聲。BERT 是一種對語言表徵進行預訓練的方法,換句話說,是經過大型文本語料庫(如維基百科)訓練後獲得的通用「語言理解」模型,該模型可用於我們最在乎的 NLP 下遊任務(如問答)。BERT 之所以表現得比過往的方法要好,是因為它是首個用於進行 NLP 預訓練的無監督、深度雙向系統。
  • 2019,不可錯過的NLP「高光時刻」
    該模型在12個 NLP任務中都達到了最優效果。,以適應不同任務。https://arxiv.org/abs/1903.08855XLNet是基於預訓練的NLP模型,它在20個任務上相較於BERT都有提升。相關總結請戳連結。
  • NLP領域最優秀的8個預訓練模型(附開源地址)
    自然語言處理應用能夠快速增長,很大程度上要歸功於通過預訓練模型實現遷移學習的概念。在自然語言處理的背景下,遷移學習本質上是在一個數據集上訓練模型,然後對該模型進行調整,以在不同的數據集上執行不同的自然語言處理功能。這一突破,使得每個人都能夠輕鬆地完成任務,尤其是那些沒有時間、也沒有資源從頭開始構建自然語言處理模型的人們。
  • 一行代碼即可調用18款主流模型!PyTorch Hub輕鬆解決論文可復現性
    探索已加載的模型從PyTorch Hub加載模型後,可以使用dir(model)查看模型的所有可用方法,示例代碼:>>> dir(model)>>>['forward'...'to''state_dict',]還可以用help(model.forward)對運行該模型所需參數有更深入的了解。
  • 【NLP】從Transformer到BERT模型
    雖然BERT有很好的表現,但本身也有一些問題。比如,BERT並不能用來生成數據。 由於BERT本身是依賴於DAE的結構來訓練的,所以不像那些基於語言模型訓練出來的模型具備很好地生成能力。之前的方法比如NNLM、ELMo是基於語言模型生成的,所以用訓練好的模型可以生成出一些句子、文本等。
  • 復旦邱錫鵬團隊最新成果fastHan:基於BERT的中文NLP集成工具
    簡介fastHan 是基於 fastNLP 與 PyTorch 實現的中文自然語言處理工具,像 spacy 一樣調用方便。其內核為基於 BERT 的聯合模型,其在 13 個語料庫中進行訓練,可處理中文分詞、詞性標註、依存句法分析、命名實體識別四項任務。
  • 被封神的多語言BERT模型是如何開啟NER新時代的?
    谷歌研究發布了經過預訓練的BERT模型,包括多語言、中文和英文BERT。會話人工智慧框架Deeppavlov是基於iPavlov開發的,它包含構建對話系統所需的所有組件。BERT發布之後,其處理多種任務的能力令人驚異。BERT可以集成到三個常用NLP任務的解決方案中:文本分類、標記和問題回答。
  • NLP之文本分類:「Tf-Idf、Word2Vec和BERT」三種模型比較
    文本分類是指根據文本數據內容對其進行分類的問題。我們有多種技術從原始文本數據中提取信息,並用它來訓練分類模型。本教程比較了傳統的詞袋法(與簡單的機器學習算法一起使用)、流行的詞嵌入模型(與深度學習神經網絡一起使用)和最先進的語言模型(和基於attention的transformers模型中的遷移學習一起使用),語言模型徹底改變了NLP的格局。
  • 谷歌最強NLP模型BERT,為何炫酷又強大?騰訊程式設計師給你從頭講起
    雖然知道了 bert能解決這個問題,我們更好奇的是"Ϊʲô":為什麼 bert 的表現能這麼好?這裡面有沒有可解釋的部分呢?因為 Multi-head-attention 是 bert 的主要組成部分,所以我們從"頭"入手,希望弄清楚各個 head 對 bert 模型有什麼作用。為了研究某個 head 對模型的影響,我們需要比較有這個 head 和沒有這個 head 模型的前後表現。
  • 基於Bert和通用句子編碼的Spark-NLP文本分類
    文本分類是現代自然語言處理的主要任務之一,它是為句子或文檔指定一個合適的類別的任務。類別取決於所選的數據集,並且可以從主題開始。每一個文本分類問題都遵循相似的步驟,並用不同的算法來解決。更不用說經典和流行的機器學習分類器,如隨機森林或Logistic回歸,有150多個深度學習框架提出了各種文本分類問題。文本分類問題中使用了幾個基準數據集,可以在nlpprogress.com上跟蹤最新的基準。以下是關於這些數據集的基本統計數據。
  • 一文看盡2019年NLP前沿突破
    https://nlp.stanford.edu/projects/glove/Transformer於2017年6月提出,是一種基於 encoder-decoder 結構的模型。無需針對性訓練就能橫掃各種特定領域的語言建模任務,還具備閱讀理解、問答、生成文章摘要、翻譯等等能力。而且,OpenAI最初還擔心項目過於強大,而選擇沒有開源。但在10個月之後,還是決定將其公布。
  • PyTorch-Transformers:最先進的自然語言處理庫(附帶python代碼)
    utm_source=blog&utm_medium=pytorch-transformers-nlp-pythonPyTorch-Transformers是什麼?PyTorch-Transformers是一個最先進的自然語言處理預訓練模型庫。我從PyTorch-Transformers的文檔中選取了這一部分。
  • 從ULMFiT、BERT等經典模型看NLP 發展趨勢
    模型,實現用一個模型處理多種NLP任務。ULMFiT 是 Universal Language Model Fine-Tuning(通用語言模型微調)的縮寫。其實根據它的名字,基本就可以知道它的操作流程,具體見上圖:一共是分為3個階段,首先是語言模型的預訓練、然後是語言模型的finetune、最後是分類任務的finetune。ULMFiT 使用新的自然語言生成技術實現了最先進的結果。
  • 搞定NLP領域的「變形金剛」!教你用BERT進行多標籤文本分類
    該模型還在兩個無監督任務(「遮蔽語言模型」和「下一句預測」)上進行了預訓練。這讓我們可以通過對下遊特定任務(例如情緒分類,意圖檢測,問答等)進行微調來使用預先訓練的BERT模型。本文將手把手教你,用BERT完成一個Kaggle競賽。在本文中,我們將重點介紹BERT在多標籤文本分類問題中的應用。
  • Pytorch-Transformers 1.0 發布,支持六個預訓練框架,含 27 個預...
    哪些支持PyTorch-Transformers(此前叫做pytorch-pretrained-bert)是面向自然語言處理,當前性能最高的預訓練模型開源庫。該開源庫現在包含了 PyTorch 實現、預訓練模型權重、運行腳本和以下模型的轉換工具:1、谷歌的 BERT,論文:「BERT: Pre-training of Deep Bidirectional Transformers for Language Understanding」,論文作者:Jacob Devlin, Ming-Wei Chang, Kenton Lee
  • PyTorch Hub發布!一行代碼調用最潮模型,圖靈獎得主強推
    圖靈獎得主Yann LeCun強烈推薦,無論是ResNet、BERT、GPT、VGG、PGAN還是MobileNet等經典模型,只需輸入一行代碼,就能實現一鍵調用。厲不厲害!Facebook官方博客表示,PyTorch Hub是一個簡易API和工作流程,為復現研究提供了基本構建模塊,包含預訓練模型庫。