(一)文字分類經典模型之CNN篇

爱编码的懒虫發表於2024-05-08

CNN源於計算機視覺研究,後來諸多學者將其應用於短文字分類,其基本結構如下圖所示:

image

由上圖可知,基於CNN的短文字分類模型,通常包括輸入層、卷積層、池化層、全連線層和輸出層五部分,其中卷積層和池化層是最為關鍵的特徵提取環節。卷積層透過構造二維卷積核,並將其上下移動,在卷積視窗內與文字表示矩陣進行卷積操作,以此來提取文字特徵。池化層則是對提取的特徵進行選擇,篩選出最為明顯的特徵。通常,在短文字分類時,需要對卷積層與池化層進行多層交替疊加,經過多次特徵提取與特徵選擇,多角度獲取文字特徵資訊;然後,進入全連線層,將特徵資訊進行整合,並將結果在輸出層展示。

image

TextCNN是Yoon Kim在2014年提出的模型,開創了用CNN編碼n-gram特徵的先河。模型結構如上圖3所示。

image

上圖是來源於2016年ACL論文A Sensitivity Analysis of (and Practitioners' Guide to) Convolutional Neural Networks for Sentence Classification

模型詳解

資料處理:所有句子padding成一個長度:seq_len

1.模型輸入[batch_size, seq_len]

2.經過embedding層載入預訓練詞向量或者隨機初始化,詞向量維度為embedding_size:[batch_size, seq_len, embedding_size]

3.卷積層:NLP中卷積核寬度與embedding_size相同,相當於一維卷積。3個尺寸的卷積核(2, 3, 4),每個尺寸的卷積核有100個,卷積後得到三個特徵圖: [batch_size, 100, seq_len -1][batch_size, 100, seq_len - 2][batch_size, 100, seq_len -3]

卷積操作相當於提取了句中的2-gram、3-gram、4-gram資訊,多個卷積是為了提取多種特徵,最大池化將提取到最重要的資訊保留。

4.池化層:對三個特徵圖做最大池化[batch_size, 100][batch_size, 100][batch_size, 100]

5.拼接[batch_size, 300]

6.全連線[batch_size, num_classes]

7.預測:Softmax歸一化,將num_class個數中最大的數對應的類作為最終預測。

TextCNN是很適合中短文字場景的強baseline,但不太適合長文字,因為卷積核尺寸通常不會設定很大,無法捕獲長距離特徵。同時max-pooling也存在侷限,會丟掉一些有用特徵。另外再仔細想的話,TextCNN和傳統的n-gram詞袋模型本質是一樣的,它的好效果很大部分來自於詞向量的引入,解決了詞袋模型的稀疏性問題。這也正是TextCNN成功的原因,TextCNN的成功並不是結構的成功,而是證明了預訓練詞向量 + 微調是提升NLP各項任務的關鍵能力(實驗結果如下圖4所示)。

image

那麼怎麼改進TextCNN模型的分類效果呢?從模型上看,無非就是以下幾個大的方面:

1.詞嵌入Embedding

2.卷積層

3.池化層

4全連線層

而Character-level Convolutional Networks for Text Classification這篇文章則從字元級卷積網路進行文字分類進行了實證探索。這個模型的優點就是模型結構簡單,並且在大語料上效果很好,可以用於各種語言,不需要做分詞處理,在噪音比較多的文字上表現較好。但是缺點就是字元級別的文字長度特別長,不利於處理長文字的分類,只使用字元級別資訊,所以模型學習語義方面的資訊較少而且在小語料上效果較差。後來學者們也研究了此問題,在論文Shallow word-level vs. deep character-level中就表明:即使在大量訓練資料的情況下,淺層字級CNN也比最先進的超深字元級CNN更準確、更快。

為了進一步提高TextCNN模型的分類效果,彌補在獲取短文字語義和上下文資訊等方面的不足,學者們試圖透過增加層數,增大了卷積核獲取資訊的視野,構建了深度CNN模型。

受這些的啟發,Tencent AI Lab在2017年提出了Deep Pyramid Convolutional Neural Networks for Text Categorization模型,從模型效能上縱向比較來看,其也比經典的TextCNN(表格的第二行ShallowCNN)有了明顯提高,在Yelp五分類情感分類任務中提升了近2個百分點。

image

image

DPCNN的模型如上圖。

模型詳解

1.模型輸入:[batch_size, seq_len]

2.經過embedding層:載入預訓練詞向量或者隨機初始化,詞向量維度為embedding_size。[batch_size, seq_len, embedding_size]

3.進行卷積,250個尺寸為3的卷積核,論文中稱這層為region embedding。[batch_size, 250, seq_len - 2]

4.接兩層卷積,每層都是250個尺寸為3的卷積核(等長卷積,先padding再卷積,保證卷積前後的序列長度不變)[batch_size, 250, seq_len - 2]

5.Repeat

a.進行大小為3,步長為2的最大池化,將序列長度壓縮為原來的二分之一。(進行取樣)

b.接兩層等長卷積,每層都是250個尺寸為3的卷積核

c.a的結果加上b的結果

重複以上操作,直至序列長度等於1。[batch_size, 250, 1]

6.全連線 + softmax歸一化:

[batch_size, num_class] ==> [batch_size, 1]

DPCNN的核心改進如下:

1.在Region embedding時不採用CNN那樣加權卷積的做法,而是對n個詞進行pooling後再加個1 * 1的卷積(這兒有疑問,檢視一下原始碼),因為實驗下來效果差不多,且作者認為前者的表示能力更強,

2.使用1/2池化層,用size=3 stride=2的卷積核,直接讓模型可編碼的sequence長度翻倍

3.殘差連線,參考ResNet,減緩梯度彌散問題。

TextCNN的過程類似於提取n-gram資訊,而且只有一層,難以捕捉長距離特徵。而DPCNN,可以看出來它的region embedding就是一個去掉池化層的TextCNN,再將卷積層疊加。

每層序列長度都減半,如圖7所示。可以這麼理解:相當於在n-gram上再做n-gram。越往後的層,每個位置融合的資訊越多,最後一層提取的就是整個序列的語義資訊。

image

上面的DPCNN是從縱向增加層數構建的深度CNN模型,那麼橫向改變模型是否可行呢?比如在論文A Convolutional Neural Network for Modelling Sentences中使用了動態池化K-Max這一概念細化了短文字特徵提取;同時,在池化層保留前K個最大特徵值,從多個維度獲取短文字特徵。

相關文章