[資訊抽取]基於ERNIE3.0的多對多資訊抽取演演算法:屬性關係抽取

2022-12-03 21:00:31

[資訊抽取]基於ERNIE3.0的多對多資訊抽取演演算法:屬性關係抽取

實體關係,實體屬性抽取是資訊抽取的關鍵任務;實體關係抽取是指從一段文字中抽取關係三元組,實體屬性抽取是指從一段文字中抽取屬性三元組;資訊抽取一般分以下幾種情況一對一,一對多,多對一,多對多的情況:

  • 一對一:「張三男漢族碩士學歷」含有一對一的屬性三元組(張三,民族,漢族)。

  • 一對多:「華揚聯眾數位技術股份有限公司於2017年8月2日在上海證券交易所上市」,含有一對多的屬性三元組(華揚聯眾數位技術股份有限公司,上市時間,2017年8月2日)和(華揚聯眾數位技術股份有限公司,上市地點,上海證券交易所上市)

  • 多對一:「上海森焱軟體有限公司和上海歐提軟體有限公司的註冊資本均為100萬人民幣」,含有多對一的屬性三元組(上海森焱軟體有限公司,註冊資本,100萬人民幣)和(上海歐提軟體有限公司,註冊資本,100萬人民幣)

  • 多對多:「大華種業稻麥種子加工36.29萬噸、銷售37.5萬噸;蘇墾米業大米加工22.02萬噸、銷售24.86萬噸」,含有多對多的屬性三元組(大華種業,稻麥種子產量,36.29萬噸)和(蘇墾米業,大米加工產量,22.02萬噸)

程式碼結構如下:


├── data
│   ├── entity_attribute_data
│   │   ├── dev_data
│   │   │   └── dev.json
│   │   ├── predict_data
│   │   │   └── predict.json
│   │   ├── test_data
│   │   │   └── test.json
│   │   └── train_data
│   │       └── train.json
│   └── entity_relation_data
│       ├── dev_data
│       │   └── dev.json
│       ├── predict_data
│       │   └── predict.json
│       ├── test_data
│       │   └── test.json
│       └── train_data
│           └── train.json
├── data_set_reader
│   └── ie_data_set_reader.py
├── dict
│   ├── entity_attribute_label_map.json
│   └── entity_relation_label_map.json
├── examples
│   ├── many_to_many_ie_attribute_ernie_fc_ch_infer.json
│   ├── many_to_many_ie_attribute_ernie_fc_ch.json
│   ├── many_to_many_ie_relation_ernie_fc_ch_infer.json
│   └── many_to_many_ie_relation_ernie_fc_ch.json
├── inference
│   ├── custom_inference.py
│   └── __init__.py
├── model
│   ├── ernie_fc_ie_many_to_many.py
│   └── __init__.py
├── run_infer.py
├── run_trainer.py
└── trainer
    ├── custom_dynamic_trainer.py
    ├── custom_trainer.py
    └── __init__.py

1.資料集簡介

這裡提供三份已標註的資料集:屬性抽取資料集(demo範例資料集)、關係抽取資料集(demo範例資料集)、DuIE2.0(全量資料集)。

  • 屬性抽取訓練集、測試集、驗證集和預測集分別存放在./data/entity_attribute_data目錄下的train_data、test_data、dev_data和predict_data資料夾下,對應的範例標籤詞表存放在./dict目錄下。

  • 關係抽取訓練集、測試集、驗證集和預測集分別存放在./data/entity_relation_data目錄下的train_data、test_data、dev_data和predict_data資料夾下,對應的範例標籤詞表存放在./dict目錄下。

  • DuIE2.0資料集已經上傳到「資料集中」也進行解壓

注:資料集(包含詞表)均為utf-8格式。

Demo範例資料集(屬性抽取資料集、關係抽取資料集)

demo範例資料集中屬性抽取資料集與關係抽取資料集的結構一樣,他們都只包含少量資料集,可用於快速開始模型的訓練與預測。

訓練集/測試集/的資料格式相同,每個樣例分為兩個部分文字和對應標籤

{"text": "倪金德,1916年生,奉天省營口(今遼寧省營口市)人", "spo_list": [{"predicate": "出生日期", "subject": [0, 3], "object": [4, 9]}, {"predicate": "出生地", "subject": [0, 3], "object": [11, 16]}]}
{"text": "基本介紹克里斯蒂娜·塞寇麗(Christina Sicoli)身高163cm,在加拿大安大略出生和長大,畢業於倫道夫學院", "spo_list": [{"predicate": "畢業院校", "subject": [4, 13], "object": [55, 60]}]}

預測集只有一個key("text"):

{"text": "倪金德,1916年生,奉天省營口(今遼寧省營口市)人"}
{"text": "基本介紹克里斯蒂娜·塞寇麗(Christina Sicoli)身高163cm,在加拿大安大略出生和長大,畢業於倫道夫學院"}

標籤詞表:標籤列表是一個json字串,key是標籤值,value是標籤對應id,範例詞表採用BIO標註,B表示關係,分為主體(S)與客體(O),如下所示:

{
     "O": 0,
     "I": 1,
     "B-畢業院校@S": 2,
     "B-畢業院校@O": 3,
     "B-出生地@S": 4,
     "B-出生地@O": 5,
     "B-祖籍@S": 6,
     "B-祖籍@O": 7,
     "B-國籍@S": 8,
     "B-國籍@O": 9,
     "B-出生日期@S": 10,
     "B-出生日期@O": 11
}

注意:O, I對應的ID必須是0, 1,B-XXX@O對應的id需要必須為B-XXX@S對應的id+1(B-XXX@s須為偶數,B-XXX@O須為奇數)
DuIE2.0資料集

DuIE2.0是業界規模最大的中文關係抽取資料集,其schema在傳統簡單關係型別基礎上新增了多元複雜關係型別,此外其構建語料來自百度百科、百度資訊流及百度貼吧文字,全面覆蓋書面化表達及口語化表達語料,能充分考察真實業務場景下的關係抽取能力。

DuIE2.0資料集的格式與本框架所需要的文字輸入格式不一致,需要進行轉化成demo範例資料集的格式才能使用,具體轉化步驟如下:下載資料集到 ./data/DuIE2.0 資料夾中,並解壓

  • 進入./data/DuIE2.0目錄

  • 執行./data/DuIE2.0/convert_data.py 指令碼

{'text': '《司馬遷之人格與風格\u3000道教徒的詩人李白及其痛苦》是李長之代表作品,共收錄了兩本著作,《司馬遷之人格與風格》,是中國第一部透過西方文學批評視角全面審視、評價司馬遷及其《史記》的學術專著', 'spo_list': [{'predicate': '作者', 'object_type': {'@value': '人物'}, 'subject_type': '圖書作品', 'object': {'@value': '李長之'}, 'subject': '司馬遷之人格與風格\u3000道教徒的詩人李白及其痛苦'}, {'predicate': '作者', 'object_type': {'@value': '人物'}, 'subject_type': '圖書作品', 'object': {'@value': '李長之'}, 'subject': '司馬遷之人格與風格 道教徒的詩人李白及其痛苦'}]}
《司馬遷之人格與風格 道教徒的詩人李白及其痛苦》是李長之代表作品,共收錄了兩本著作,《司馬遷之人格與風格》,是中國第一部透過西方文學批評視角全面審視、評價司馬遷及其《史記》的學術專著 * 司馬遷之人格與風格 道教徒的詩人李白及其痛苦

2.網路模型選擇(文心大模型)

文心預置的可用於生成任務的模型原始檔在/home/aistudio/model/ernie_fc_ie_many_to_many.py

網路名稱(py檔案的型別) 簡介 支援型別
ErnieFcIe(ernie_fc_ie_many_to_many.py) ErnieFcIe多對多資訊抽取任務模型原始檔,可載入ERNIE2.0-Base、ERNIE2.0-large、ERNIE3.0-Base、ERNIE3.0-x-Base、ERNIE3.0-Medium 通用資訊抽取Finetune任務

ERNIE預訓練模型下載:文心提供的ERNIE預訓練模型的引數檔案和組態檔在 /home/aistudio/models_hub目錄下,使用對應的sh指令碼,即可拉取對應的模型、字典、必要環境等檔案。

簡單羅列可能會用的模型:

模型名稱 下載指令碼 備註
ERNIE1.0-m-Base Text ERNIE-M:通過將跨語言語意與單語語料庫對齊來增強多語言表示
ERNIE1.0-gen-Base Text ERNIE-GEN:用於自然語言生成的增強型多流預訓練和微調框架
ERNIE2.0-Base Text
ERNIE2.0-large Text
ERNIE3.0-Base Text
ERNIE3.0-x-Base Text
ERNIE3.0-Medium Text 下載並解壓後得到對應模型的引數、字典和設定

簡單介紹以下幾個不常用模型:

ERNIE-GEN 是面向生成任務的預訓練-微調框架,首次在預訓練階段加入span-by-span 生成任務,讓模型每次能夠生成一個語意完整的片段。在預訓練和微調中通過填充式生成機制和噪聲感知機制來緩解曝光偏差問題。此外, ERNIE-GEN 取樣多片段-多粒度目標文字取樣策略, 增強源文字和目標文字的關聯性,加強了編碼器和解碼器的互動。

ERNIE-GEN base 模型和 ERNIE-GEN large 模型。 預訓練資料使用英文維基百科和 BookCorpus,總共16GB。此外,我們還發布了基於 430GB 語料(資料描述見ERNIE-GEN Appendix A.1)預訓練的ERNIE-GEN large 模型。

  • ERNIE-GEN base (lowercased | 12-layer, 768-hidden, 12-heads, 110M parameters)
  • ERNIE-GEN large (lowercased | 24-layer, 1024-hidden, 16-heads, 340M parameters)
  • ERNIE-GEN large with 430G (lowercased | 24-layer, 1024-hidden, 16-heads, 340M parameters)

微調任務:在五個典型生成任務上與當前效果最優的生成預訓練模型(UniLM、MASS、PEGASUS、BART、T5等)進行對比, 包括生成式摘要 (Gigaword 和 CNN/DailyMail), 問題生成(SQuAD), 多輪對話(Persona-Chat) 和生成式多輪問答(CoQA)。

https://github.com/PaddlePaddle/ERNIE/blob/repro/ernie-gen/README.zh.md

ERNIE-M 是面向多語言建模的預訓練-微調框架。為了突破雙語語料規模對多語言模型的學習效果限制,提升跨語言理解的效果,我們提出基於回譯機制,從單語語料中學習語言間的語意對齊關係的預訓練模型 ERNIE-M,顯著提升包括跨語言自然語言推斷、語意檢索、語意相似度、命名實體識別、閱讀理解在內的 5 種典型跨語言理解任務效果。

飛槳釋出了 ERNIE-M base 多語言模型和 ERNIE-M large 多語言模型。

  • ERNIE-M base (12-layer, 768-hidden, 12-heads)
  • ERNIE-M large (24-layer, 1024-hidden, 16-heads)

下游任務:在自然語言推斷,命名實體識別,閱讀理解,語意相似度以及跨語言檢索等任務上選取了廣泛使用的資料集進行模型效果驗證,並且與當前效果最優的模型(XLM、Unicoder、XLM-R、INFOXLM、VECO、mBERT等)進行對比。

https://github.com/PaddlePaddle/ERNIE/blob/repro/ernie-m/README_zh.md

3.訓練&預測

3.1 屬性抽取模型訓練&預測

以屬性抽取資料集的訓練為例:

訓練的組態檔:

組態檔:./examples/many_to_many_ie_attribute_ernie_fc_ch.json

{
  "dataset_reader": {
    "train_reader": {
      "name": "train_reader",
      "type": "IEReader",
      "fields": [],
      "config": {
        "data_path": "./data/entity_attribute_data/train_data/",
        "shuffle": false,
        "batch_size": 2,
        "epoch": 5,
        "sampling_rate": 1.0,
        "need_data_distribute": true,
        "need_generate_examples": false,
        "extra_params": {
          "vocab_path": "./models_hub/ernie_3.0_base_ch_dir/vocab.txt",        #選擇對應預訓練模型的詞典路徑,在models_hub路徑下
          "label_map_config": "./dict/entity_attribute_label_map.json",
          "num_labels": 12,
          "max_seq_len": 512,
          "do_lower_case":true,
          "in_tokens":false,
          "tokenizer": "FullTokenizer"
        }
      }
    },
    "test_reader": {
      "name": "test_reader",
      "type": "IEReader",
      "fields": [],
      "config": {
        "data_path": "./data/entity_attribute_data/test_data/",
        "shuffle": false,
        "batch_size": 2,
        "epoch": 1,
        "sampling_rate": 1.0,
        "need_data_distribute": false,
        "need_generate_examples": false,
        "extra_params": {
          "vocab_path": "./models_hub/ernie_3.0_base_ch_dir/vocab.txt",  #選擇對應預訓練模型的詞典路徑,在models_hub路徑下
          "label_map_config": "./dict/entity_attribute_label_map.json",
          "num_labels": 12,
          "max_seq_len": 512,
          "do_lower_case":true,
          "in_tokens":false,
          "tokenizer": "FullTokenizer"
        }
      }
    }
  },
  "model": {
    "type": "ErnieFcIe",
    "is_dygraph":1,
    "num_labels":12,
    "optimization": {
      "learning_rate": 5e-05,
      "use_lr_decay": true,
      "warmup_steps": 0,
      "warmup_proportion": 0.1,
      "weight_decay": 0.01,
      "use_dynamic_loss_scaling": false,
      "init_loss_scaling": 128,
      "incr_every_n_steps": 100,
      "decr_every_n_nan_or_inf": 2,
      "incr_ratio": 2.0,
      "decr_ratio": 0.8
    },
    "embedding": {
      "config_path": "./models_hub/ernie_3.0_base_ch_dir/ernie_config.json"  #選擇對應預訓練模型的組態檔路徑,在models_hub路徑下
    }
  },
  "trainer": {
    "type": "CustomDynamicTrainer",
    "PADDLE_PLACE_TYPE": "gpu",
    "PADDLE_IS_FLEET": 0,
    "train_log_step": 10,
    "use_amp": true,
    "is_eval_dev": 0,
    "is_eval_test": 1,
    "eval_step": 50,
    "save_model_step": 100,
    "load_parameters": "",
    "load_checkpoint": "",
    "pre_train_model": [
      {
        "name": "ernie_3.0_base_ch",
        "params_path": "./models_hub/ernie_3.0_base_ch_dir/params"   #選擇對應預訓練模型的引數路徑,在models_hub路徑下
      }
    ],
    "output_path": "./output/ie_attribute_ernie_3.0_base_fc_ch",    #輸出路徑
    "extra_param": {
      "meta":{
        "job_type": "entity_attribute_extraction"
      }
    }
  }
}
# 基於範例的資料集,可以執行以下命令在訓練集(train.txt)上進行模型訓練,並在測試集(test.txt)上進行驗證;
# 訓練屬性抽取
%cd /home/aistudio
!python run_trainer.py --param_path ./examples/many_to_many_ie_attribute_ernie_fc_ch.json
# 訓練執行的紀錄檔會自動儲存在./log/test.log檔案中;
# 訓練中以及結束後產生的模型檔案會預設儲存在./output/目錄下,其中save_inference_model/資料夾會儲存用於預測的模型檔案,save_checkpoint/資料夾會儲存用於熱啟動的模型檔案

部分結果展示:

INFO: 11-30 15:19:47: custom_dynamic_trainer.py:85 * 139681516312320 current learning rate: 2e-07
DEBUG: 11-30 15:19:48: ernie_fc_ie_many_to_many.py:234 * 139681516312320 phase = training precision = 1.0 recall = 1.0 f1 = 1.0 step = 2500            time_cost = 0.5210211277008057 loss = [0.00099489]
INFO: 11-30 15:19:48: custom_dynamic_trainer.py:85 * 139681516312320 current learning rate: 0.0
DEBUG: 11-30 15:19:48: ernie_fc_ie_many_to_many.py:261 * 139681516312320 phase = test precision = 0.958 recall = 0.976 f1 = 0.967 time_cost = 0.4507319927215576
INFO: 11-30 15:19:48: custom_dynamic_trainer.py:138 * 139681516312320 eval step = 14
INFO: 11-30 15:19:48: custom_dynamic_trainer.py:103 * 139681516312320 Final test result: 
DEBUG: 11-30 15:19:49: ernie_fc_ie_many_to_many.py:261 * 139681516312320 phase = test precision = 0.958 recall = 0.976 f1 = 0.967 time_cost = 0.44904589653015137
INFO: 11-30 15:19:49: custom_dynamic_trainer.py:138 * 139681516312320 eval step = 14

使用預置網路進行預測的方式為使用./run_infer.py入口指令碼,通過--param_path引數來傳入./examples/目錄下的json組態檔。

預測分為以下幾個步驟:

  • 基於範例的資料集,可以執行以下命令在預測集(predict.txt)上進行預測:

  • 預測執行的紀錄檔會自動儲存在./output/predict_result.txt檔案中。

以屬性抽取資料集的預測為例:

預測的組態檔

  • 組態檔:./examples/many_to_many_ie_attribute_ernie_fc_ch_infer.json

  • 在組態檔./examples/many_to_many_ie_attribute_ernie_fc_ch_infer.json中需要更改 inference.inference_model_path 為上面訓練過程中所儲存的預測模型的路徑

{
  "dataset_reader": {
      "predict_reader": {
          "name": "predict_reader",
          "type": "IEReader",
          "fields": [],
          "config": {
              "data_path": "./data/entity_attribute_data/predict_data/",
              "shuffle": false,
              "batch_size": 2,
              "epoch": 1,
              "sampling_rate": 1.0,
              "extra_params": {
                  "vocab_path": "../../models_hub/ernie_3.0_base_ch_dir/vocab.txt",
                  "label_map_config": "./dict/entity_attribute_label_map.json",
                  "num_labels": 12,
                  "max_seq_len": 512,
                  "do_lower_case":true,
                  "in_tokens":false,
                  "tokenizer": "FullTokenizer",
                  "need_data_distribute": false,
                  "need_generate_examples": true
              }
          }
      }
  },

  "inference": {
      "output_path": "./output/predict_result.txt",               #輸出檔案路徑
      "label_map_config": "./dict/entity_attribute_label_map.json",
      "PADDLE_PLACE_TYPE": "gpu",
      "inference_model_path": "./output/ie_attribute_ernie_3.0_base_fc_ch/save_inference_model/inference_step_1000",   #載入推理模型
      "extra_param": {
          "meta": {
              "job_type": "information_extraction"
          }
      }
  }
}

3.2 關係抽取模型訓練&預測

# 訓練關係抽取
!python run_trainer.py --param_path ./examples/many_to_many_ie_relation_ernie_fc_ch.json
# 訓練執行的紀錄檔會自動儲存在./log/test.log檔案中;
# 訓練中以及結束後產生的模型檔案會預設儲存在./output/目錄下,其中save_inference_model/資料夾會儲存用於預測的模型檔案,save_checkpoint/資料夾會儲存用於熱啟動的模型檔案

部分結果展示:

DEBUG: 11-30 16:09:37: ernie_fc_ie_many_to_many.py:261 * 140264317826816 phase = test precision = 0.953 recall = 0.968 f1 = 0.96 time_cost = 0.7550814151763916
INFO: 11-30 16:09:37: custom_dynamic_trainer.py:138 * 140264317826816 eval step = 50
INFO: 11-30 16:09:41: dynamic_trainer.py:170 * 140264317826816 save path: ./output/ie_relation_ernie_3.0_medium/save_inference_model/inference_step_2500
INFO: 11-30 16:09:42: custom_dynamic_trainer.py:103 * 140264317826816 Final test result: 
DEBUG: 11-30 16:09:43: ernie_fc_ie_many_to_many.py:261 * 140264317826816 phase = test precision = 0.953 recall = 0.968 f1 = 0.96 time_cost = 0.883291482925415
INFO: 11-30 16:09:43: custom_dynamic_trainer.py:138 * 140264317826816 eval step = 50

部分結果:

"text": "楊力革,男,漢族,1966年4月生,湖南益陽人,1987年7月參加工作,1992年10月入黨,在職研究生學歷(2004年7月新疆自治區黨委黨校領導幹部研究生班工商管理專業畢業)",
   "spo_list": [
    {
     "predicate": "出生地",
     "subject": [
      0,
      3
     ],
     "object": [
      18,
      22
     ]
    },
    {
     "predicate": "出生日期",
     "subject": [
      0,
      3
     ],
     "object": [
      9,
      16
     ]
    }
   ]

4.總結

本專案講解了基於ERNIE資訊抽取技術,對屬性和關係的抽取涉及多對多抽取,主要是使用可ERNIEKIT元件,整體效果非常不錯,當然追求小樣本學習的可以參考之前UIE專案或者去官網看看paddlenlp最新的更新,對訓練和部署進行了提速。

模型 任務 precision recall f1
ernie_3.0_medium 屬性抽取 0.958 0.976 0.967
ernie_3.0_medium 關係抽取 0.953 0.968 0.96