基于對比學習(Contrastive Learning)的文本表示模型【為什么】能學到語義【相似】度?
共 1666字,需瀏覽 4分鐘
·
2022-02-09 17:37
我最近在做對比學習相關的實踐,折騰了好久,調來調去效果一般,甚是煩躁。以下主要是一些個人的體會,思路會比較逆向。
回答這個問題,要從語義相似度計算的一般范式說起。計算句子A和句子B的語義相似度,通常來說,基于交互的方案結果更準確:

如果一共有N個句子,那么就需要進行 N × (N-1) 次相似度計算。在絕大多數(shù)的工程落地場景中,這樣的計算開銷都是無法被接受的。因此,建模只能轉向基于表示的“兩步走”方案:

每個輸入句子,先要經過一個編碼器進行量化,再由一個輕量級的判定模塊進行相似度輸出。這樣設計的好處是,偏“重”的編碼部分可以離線計算并緩存結果,只需計算 N 次。相似度判定部分,雖然仍是 N × (N-1) 次計算,但采用的是余弦等非神經網絡的形式,即使放在線上實時進行也可以承受。
這樣“前重后輕”的結構,缺乏兩個句子間的深度交互。前置神經網絡在編碼時,無法提前獲知當前句子將和什么樣的目標句子做比較,難以判斷語義建模的重點是在哪個文本片段。比如,以下是 SemEval-2016 的一組標題:
A: Mandela's condition has 'improved'(曼德拉的狀態(tài)有所好轉)
B: Mandela's condition has 'worsened over past 48 hours'(曼德拉在過去48小時每況愈下)
單看 A 句,如果編碼器將句子抽象為“曼德拉的狀況波動”,似乎也可以接受,但是結合 B 句一起看,就出現(xiàn)了嚴重的信息取舍錯誤。
總結來說,由于使用了不可學習的余弦相似度作為度量,并且完全去除了編碼部分的交互耦合,基于表示的方案無法進行 task-specific 式的模型學習。語義相似度的求解,轉換成了一個單純的特征映射過程:編碼器提取輸入句子的語義信息,再將它投影到向量空間中。‘
這有點像傳統(tǒng)機器學習領域的問題。在理想情況下,所有句子在該空間的分布,應當滿足 alignment 和 uniformity。即,語義相似的句子彼此聚集,語義無關的句子均勻分布。
為了達成這一目標,模型需要盡可能多地提前認識各種各樣的數(shù)據(jù)。鑒于訓練數(shù)據(jù)不好找,只能自行構造,于是誕生了“自監(jiān)督訓練”,“對比學習”也是其中的一種形式。這套流程最早是從計算機視覺里來的,用于圖像向量化:

通過人為進行數(shù)據(jù)增強,讓模型抵抗表層噪聲,聚焦核心信息。回到 NLP 里,也有類似方法:

自監(jiān)督通常主要有兩類,一種是生成式,比如經典的 Mask-LM;一種是這里用的分類式。對于某個句子 X,按照上述流程構建“正例對”(X,X'),從 batch 里隨機一個其他句子構建“負例對”(X,Y)。如此一來,便可以批量生產訓練數(shù)據(jù)。
我自己在實踐的時候,起初比較偷懶,就是這樣直接處理的。正例對的相似度為1,負例對的相似度為0。但是,學習效果很差,和以往單句場景的經驗完全不一致。我猜測,真正的標注訓練數(shù)據(jù)相比,構造而成的“偽樣本對”有兩個隱患:
1. 針對性不強:正樣本由數(shù)據(jù)增強生成,豐富度有限;負樣本隨機配對,暗含[任意組合都輸出0]的錯誤誘導;
2. 標簽不準確:沒有經過人工校對,正樣本的相似度未必就是1,很有可能只有0.5或者干脆就完全相反;負樣本也極有可能隨機到語義相似的句子;
因此,需要明確分類標簽的交叉熵,就不適合作為相似度自監(jiān)督任務的損失函數(shù)。我們需要一種更寬松的約束條件,來達成更準確的學習目標。對比學習正是如此,它的核心訴求是:
>score(X,Y) \\" eeimg="1" loading="lazy"> 配套的損失函數(shù),有點像排序問題,是一個多路的softmax交叉熵,稱為 InfoNCE。假設有1個正例組合(X,X')和N個負例組合(X,Y):
在 loss->0的時候,log內部->1,分子和分母互相逼近,由于含有共同的部分(X,X'),會讓正例得分越來越大,負例越來越小,從而拉開彼此的差距。也就是常說的“正例拉近,負例推遠”,正好契合語義特征空間 alignment 和 uniformity 的目標。
