之前沒認真打過煉丹的比賽,這次機緣巧合碰上了三個牛逼又靠譜的隊友,就堅持把這次比賽打完了。剛開始的時候沒想到這次能拿下第一,趁著剛答辯完就順帶把這次NLP賽道的方案開源出來,歡迎各位同學參考和討論。
賽題分析
賽題介紹
這次的比賽由NLP和推薦兩部分組成,推薦的特征工程實在是做不明白,這次主要還是做NLP的部分。
抄一下官網的NLP賽題介紹:面向實體對象的文本描述情感極性及色彩強度分析。情感極性和強度分為五種情況:極正向、正向、中立、負向、極負向。選手需要針對給定的每一個實體對象,從文本描述的角度,分析出對該實體的情感極性和強度。
NLP任務的評價指標為macro-F1,在計算準確和召回的時候,是按照分析的實體數進行計數的,而非樣本數。
拿一條數據來舉例子(截取部分文本):
{ "content": "離婚之后的林慶昆本以為會有一番更大的天地,沒想到離開了吳敏自己什么都不是......", "entity": {"吳敏": 1, "林慶昆": -1} }
這條數據里有一段文本和兩個實體,需要預測出這兩個實體在文本中的情感極性,情感標簽為-2, -1, 0, 1, 2五個。
簡單分析可以知道這題可以定義為Aspect-level Sentiment Classification。
數據分析
在正式建模之前需要進行一些簡單的數據分析來挖掘賽題的特點。在這里截取一張和隊友一起做的PPT的圖:
數據分析
我們對數據中的文本長度、實體數量和標簽分布進行了簡單的分析,這提示我們:
有部分文本長度超過BERT的512最大長度,或許可以考慮長文本處理的常用技巧;
實體的情感標簽分布不平衡,最少的類只有2%左右,或許可以考慮不平衡分類問題的技巧。
但實驗證明上面這些考慮最后都只會成為掉分點,具體的思考在后文論述。
模型構建
Baseline
官方公布了賽題的Baseline,NLP賽道的Baseline大致是如下思路:將一段文本和文本中的一個實體拼成一條數據,一段文本對應N個實體就會有N條數據。將一條數據輸入BERT-based分類器后輸出一個實體。
仍然以上一節的case為例,按Baseline的做法這條數據會被拆成兩條數據輸入到BERT:
[CLS] 吳敏 [SEP] 離婚之后的林慶昆本以為會有一番更大的天地,沒想到離開了吳敏自己什么都不是... [SEP] [CLS] 林慶昆 [SEP] 離婚之后的林慶昆本以為會有一番更大的天地,沒想到離開了吳敏自己什么都不是... [SEP]
然后以BERT輸出的[CLS]位置的語義向量通過MLP分類器得到情感極性。
實際上我想思路的時候我還沒看到Baseline,看到Baseline的做法之后我就搖頭。
這里再截一張PPT的圖說明Baseline有什么問題:
就是說,一方面預期效果不好,因為Baseline構造數據的方式使分布發生了變化(有一個實體的文本模型會看它一次,有30個實體的文本模型就會看它30次,但是這點也存疑,因為答辯過程中有選手表示發現了數據的leak,后續的方法可能是使用了這個leak所以效果才會好的);另一方面把一段文本復制了好多遍顯然會導致效率大大下降;還有一點在PPT里沒說的是沒有考慮到實體之間可能存在的潛在關系。
設計思路
再從PPT里截一張圖:
在做這題的時候我就會思考如何做得優雅,最好方法是simple yet effective的。最好就是使用以預訓練BERT為backbone的分類器,不對模型結構做太大修改,而且還要能在一次輸入之內就并行分類所有實體。
除了BERT還考慮使用XLNet,因為XLNet使用了相對位置編碼,可以原生支持超長文本的輸入,而且XLNet的Tokenizer是字詞結合的,可以適應本次比賽文本長度較長的情況。
模型架構
大概想了不到一個小時,想到了如下的方案:
如圖所示,模型的整體架構就是一個普通的分類模型,在預訓練的BERT或XLNet模型基礎上增加了簡單的MLP分類器。這個思路的要點在于改變數據輸入的方式,利用BERT和XLNet作為Masked Language Model的性質,以[SEP]符號為界,第一段為文本輸入,第二段按順序輸入所有實體,實體之間以[MASK]進行分隔,這個[MASK]標簽通過BERT Encoder得到的語義向量就代表對應實體的情感極性。將所有[MASK]位置的語義向量通過分類器即可并行對所有的實體進行分類。
這套思路不加Trick的情況下線上F1就可以到69+,讓我在比賽前期就能超過大部分使用Baseline的團隊。
另外根據線下指標推測最終Accuracy在90+,說明這題訓練和測試集基本上同分布。
一些補充的思考
要說這個方法為什么會有用,我一開始推測是因為考慮了實體之間的潛在關系,而且對數據分布的假設更加合理。
后來決賽答辯的時候聽到有選手提到這個數據存在leak,也就是在數據中標簽非0的實體會被排在前面,標簽為0的實體會被排在后面。我突然就覺得這可能就是這個方法提升巨大的真正原因,用了這個方法之后,相當于模型從中學到了一個bias,就是靠近文本末尾的實體,標簽為0的可能性更大。
另外,在比賽中期,“靈境”組在討論區公開了一個方案,我們發現該方案的核心思路和我們不謀而合。在該方案公開后很多隊伍的分數都追上來了,在決賽答辯過程中我也發現很多高分團隊都搬運了這套方案。公開的方案和我們做法基本一致,不過使用了一個含有MLM的全套BERT類模型,第二段文本(在該方案中被稱為Prompt)的形式為:“在這句話中,<實體1>是[MASK],<實體2>是[MASK]......”,然后MLM頭輸出詞表大小維度(21128)的向量,取五個Token作為Verbalizer(壞、差、平、行、好),分別對應五個情感極性標簽,忽略其他的Token。
然而,這套方案和我們的做法還存在一定差別,這也是我認為該方案在這個任務上存在的一些問題:
我們不稱輸入的第二段文本為"Prompt",因為這容易和Prompt Tuning概念中的Prompt混淆。該任務并不適合Prompt Tuning范式,而仍然是采用普通的對全模型進行參數更新的Full Tuning范式。因此在該題中,“Prompt”的形式如何并不重要,增加一些沒什么用的詞反而會擠占第一段文本的輸入長度。
該方案使用了BERT的MLM頭進行分類,21128維的詞表中只有五個Token映射到有效標簽,其余Token都被忽略。這和我們的方案在結構上基本等價,唯一的區別是該方案有MLM頭的參數初始化而我們的分類層為隨機初始化,這個區別是否會帶來性能提升不知道,但是直觀的是模型增加了至少768*21123=16M(或者1024*21123=22M)的無用參數量,在題目有模型總大小限制的情況下這意味著可以融合的模型變少了。
模型優化
針對上述提出的模型,我們進行了很多優化嘗試,下面主要討論上分較多的技巧,沒什么用的東西就在最后放一小節補充說明。很多優化技巧都會導致訓練或測試階段時空開銷大大提升,比賽時還是應該視情況使用。
線下數據劃分方式
隊友發現,初賽階段使用前90%數據訓練,后10%驗證,可以取得最好的線上效果,隨機10%效果會變差一些,增加訓練數據也不能使效果變好。復賽階段使用了同樣的數據劃分方式。
對抗訓練(FGM)
在各類文本分類任務中,常用的提升NLP模型訓練魯棒性和泛化能力的有效方法。簡單來說是在Embedding層的參數有一定程度擾動時也盡量保證模型能分類正確。事后估計初賽線上提升1%左右。
參考了這篇知乎文章的實現方法:Nicolas:【煉丹技巧】功守道:NLP中的對抗訓練 + PyTorch實現
模型平均 (SWA)
對訓練過程中的多個checkpoint進行權重平均,或許可以有助于模型收斂到loss landscape平坦區域的中心,提升模型的泛化能力。具體而言,我們在驗證指標的最高點開始,將這一輪和到Early Stopping之前的各輪驗證時,驗證指標與最高點差值小于一定值的模型權重放進來平均。事后估計初賽線上提升1%左右。
模型融合
沒什么好說的,幾個模型預測的logits平均得到最終結果。值得注意的是這題有2G的模型總大小限制,因此我們需要考慮融合模型的異構度不能盲目做K折,最后融合了2個稍微異構的XLNet-Mid + 1個MacBERT-Large + 1個RoBERTa-Large,全部保存為FP16格式,模型文件總大小2043M正好小于2G。估計初賽提升大約1%,復賽提升大約2%。
偽標簽
在模型融合的基礎上,使用融合模型預測的測試集標簽作為偽標簽,將測試集數據加入訓練集中再次訓練模型。在復賽中,我們為了避免多模型在測試集上的預測結果失去異構性,我們沒有把全部測試數據都加入訓練集,而是四個模型預測結果投票,大于等于三個模型預測一致的數據才會被加入訓練集。這個訓練集會重新被用于訓練四個模型,然后重新進行融合。復賽在模型融合基礎上還有1%左右的提升。
復賽數據適配
如圖所示。在復賽開始的時候,起初我們使用初賽訓練集+復賽訓練集的全量訓練數據對模型進行訓練,結果發現效果不好。后來發現復賽數據相比初賽數據的分布可能發生了較大的偏移,因此我們考慮用初賽訓練好的模型的權重來對模型進行初始化,然后只在復賽數據集上訓練。相比全量數據訓練提升近3%,驗證了我們的猜想。
沒什么用的
R-Drop:在有了FGM,SWA等東西的情況下沒有什么提升,而且還慢。
PGD:慢而且相比FGM沒什么提升。
EMA:有了SWA之后也顯得沒用。
數據增強:嘗試了EDA和AEDA,本來以為會有用實際上沒用。
長文本處理:估計是沒有什么用,某次偶然發現設置最大長度512的XLNet和最大長度800的XLNet相比效果基本沒有差別,用MacBERT和RoBERTa訓的模型和XLNet比效果也相差不大。推測可能是因為前半段文本的信息量已經足夠對絕大多數實體正確分類了。
標簽不平衡處理:嘗試過Focal Loss和類別重加權,也沒有什么用。猜測可能是因為數據中2和-2的數據量也相對充足(各有幾千個實體),在普通Cross Entropy下充分學習也可以對這些類大部分樣本正確分類了,而修改Loss反而會扭曲模型學習到的分布,對于訓練和測試同分布的情況下反而不利。
評測結果
初賽、復賽和決賽評測均為NLP賽道第一。
審核編輯 :李倩
-
數據分析
+關注
關注
2文章
1452瀏覽量
34077 -
nlp
+關注
關注
1文章
489瀏覽量
22058
原文標題:競賽 | Aspect-based的情感分析任務第一名方法解讀 -- 2022搜狐校園算法大賽
文章出處:【微信號:zenRRan,微信公眾號:深度學習自然語言處理】歡迎添加關注!文章轉載請注明出處。
發布評論請先 登錄
相關推薦
評論