Bert 原始碼各個檔案詳解

2021-10-06 23:57:16 字數 2965 閱讀 1968

如下圖所示,modeling.py定義了bert模型的主體結構,即從input_ids(句子中詞語id組成的tensor)sequence_output(句子中每個詞語的向量表示)以及pooled_output(句子的向量表示)的計算過程,是其它所有後續的任務的基礎。如文字分類任務就是得到輸入的input_ids後,用bertmodel得到句子的向量表示,並將其作為分類層的輸入,得到分類結果。

modeling.py的31-106行定義了乙個bertconfig類,即bertmodel的配置,在新建乙個bertmodel類時,必須配置其對應的bertconfig。bertconfig類包含了乙個bertmodel所需的超引數,除詞表大小vocab_size外,均定義了其預設取值。bertconfig類中還定義了從python dict和json中生成bertconfig的方法以及將bertconfig轉換為python dict 或者json字串的方法。

107-263行定義了乙個bertmodel類。bertmodel類初始化時,需要填寫三個沒有預設值的引數:

另外還有input_mask,token_type_ids和use_one_hot_embeddings,scope四個可選引數,scope引數會影響計算圖中tensor的名字字首,如不填寫,則字首為」bert」。在下文中,其餘引數會在使用時進行說明。

bertmodel的計算都在__init__函式中完成。計算流程如下:

為了不影響原config物件,對config進行deepcopy,然後對is_training進行判斷,如果為false,則將config中dropout的概率均設為0。

定義input_mask和token_type_ids的預設取值(前者為全1,後者為全0),shape均和input_ids相同。二者的用途會在下文中提及。

使用embedding_lookup函式,將input_ids轉化為向量,形狀為[batch_size, seq_length, embedding_size],這裡的embedding_table使用tf.get_variable,因此第一次呼叫時會生成,後續都是直接獲取現有的。此處use_one_hot_embedding的取值只影響embedding_lookup函式的內部實現,不影響結果。

呼叫embedding_postprocessor對輸入句子的向量進行處理。這個函式分為兩部分,先按照token_type_id(即輸入的句子中各個詞語的type,如對兩個句子的分類任務,用type_id區分第乙個句子還是第二個句子),lookup出各個詞語的type向量,然後加到各個詞語的向量表示中。如果token_type_id不存在(即不使用額外的type資訊),則跳過這一步。其次,這個函式計算position_embedding:即初始化乙個shape為[max_positition_embeddings, width]的position_embedding矩陣,再按照對應的position加到輸入句子的向量表示中。如果不使用position_embedding,則跳過這一步。最後對輸入句子的向量進行layer_norm和dropout,如果不是訓練階段,此處dropout概率為0.0,相當於跳過這一步。

根據輸入的input_mask(即與句子真實長度匹配的mask,如batch_size為2,句子實際長度分別為2,3,則mask為[[1, 1, 0], [1, 1, 1]]),計算shape為[batch_size, seq_length, seq_length]的mask,並將輸入句子的向量表示和mask共同傳給transformer_model函式,即encoder部分。

transformer_model函式的行為是先將輸入的句子向量表示reshape成[batch_size * seq_length, width]的矩陣,然後迴圈呼叫transformer的前向過程,次數為隱藏層個數。每次前向過程都包含self_attention_layer、add_and_norm、feed_forward和add_and_norm四個步驟,具體資訊可參考transformer的**。

獲取transformer_model最後一層的輸出,此時shape為[batch_size, seq_length, hidden_size]。如果要進行句子級別的任務,如句子分類,需要將其轉化為[batch_size, hidden_size]的tensor,這一步通過取第乙個token的向量表示完成。這一層在**中稱為pooling層。

bertmodel類提供了介面來獲取不同層的輸出,包括:

modeling.py的其餘部分定義了上面的步驟用到的函式,以及啟用函式等。

這個模組可以用於配置和啟動基於bert的文字分類任務,包括輸入樣本為句子對的(如mrpc)和輸入樣本為單個句子的(如cola)。

模組中的內容包括:

這個模組用於bert模型的預訓練,即使用masked language model和next sentence的方法,對bert模型本身的引數進行訓練。如果使用現有的預訓練bert模型在文字分類/問題回答等任務上進行fine_tune,則無需使用run_pretraining.py。

此處定義了如何將普通文字轉換成可用於預訓練bert模型的tfrecord檔案的方法。如果使用現有的預訓練bert模型在文字分類/問題回答等任務上進行fine_tune,則無需使用create_pretraining_data.py。

此處定義了對輸入的句子進行預處理的操作,預處理的內容包括:

這個模組可以配置和啟動基於bert在squad資料集上的問題回答任務。

這個模組可以使用預訓練的bert模型,生成輸入句子的向量表示和輸入句子中各個詞語的向量表示(類似elmo)。這個模組不包含訓練的過程,只是執行bert的前向過程,使用固定的引數對輸入句子進行轉換

這個模組配置了用於bert的optimizer,即加入weight decay功能和learning_rate warmup功能的adamoptimizer。

bert原始碼詳解

1 bert結構 2 句子token 原始輸入my dog is cute bert的token方式有3種,basictoken,peicetoken,fulltoken 在這篇部落格中,作者進行了論述 4 output 5 任務 mlm nsp mlm任務中被選15 的 for index in ...

ArrayList原始碼詳解

成員變數的宣告 成員變數的宣告 private static final object empty elementdata transient object elementdata 儲存元素的陣列 private static final int default capacity 10 構造方法初始...

HashMap原始碼詳解

成員變數static final int default initial capacity 1 4 aka 16 static final int maximum capacity 1 30 aka 2 30 static final float default load factor 0.75f ...