1. 程式人生 > >憑什麽相信你,我的CNN模型

憑什麽相信你,我的CNN模型

當前 像素個數 容易 cati regress 發出 ear 描述 上線

背景

學術界一直困惑的點是"如何讓看似黑盒的CNN模型說話",即對它的分類結果給出解釋。

這裏的解釋是指,讓模型告訴我們它是通過圖片的哪些像素做出判斷的,並不是深度學習理論層面的解釋。

反卷積和導向反向傳播

CNN模型的可解釋問題,很早就有人在研究了,嚴格來說只是“CNN可視化”。有兩個經典的方法。

CNN中的卷積、反卷機和反池化

反卷機(Deconvolution)、上采樣(Unsampling)、上池化(Unpooling)

技術分享圖片

UnPooling的過程,特點是在Maxpooling的時候保留最大值的位置信息,之後在unPooling階段使用該信息擴充FeatureMap,除最大值位置以外,其余補0。

UnSampling階段沒有使用MaxPooling時的位置信息,而是直接將內容復制來擴充Feature Map。
反卷積是卷積的逆過程,又稱作轉置卷積。最大的區別在於反卷積過程是有參數要進行學習的(類似卷積過程),理論是反卷積可以實現UnPooling和unSampling,只要卷積核的參數設置的合理。

卷積層回顧

特征輸入為i,卷積核尺寸為k,步長為s,padding為p。\(i=6,k=3,p=1,s=2\)的卷積過程如下:
技術分享圖片
輸出特征層的尺寸為\(o=(i+2p-k)/s+1\)

反卷積層

考慮將\(i=4,k=3,s=1\)卷積得到\(o=2\)

技術分享圖片

可以將3x3的卷積核展開為4x16的矩陣C.

技術分享圖片

CX=Y便是上述卷積過程。可見,卷積層的計算實質可以轉化為矩陣的乘法。

值得註意的是,在一些深度學習網絡的開源框架中並不是通過這種這個轉換方法來計算卷積的,因為這個轉換會存在很多無用的0乘操作,Caffe中具體實現卷積計算的方法可參考:Implementing convolution as a matrix multiplication。這是一個toeplitz 托普利茲矩陣。

我們很容易理解卷積層的前向傳播是和矩陣C線程,那麽反向傳播便是和它的轉置相乘。

反卷積和卷積的關系:卷積層的前向傳播過程就是反卷積層的反向傳播過程,卷積層的反向傳播過程就是反卷積層的前向傳播過程。

反卷機的計算

在步長s=1的情況下,反卷積核卷積過程剛好相反。結果會忽略padding的邊(p=2)。

技術分享圖片

反卷積有時候也被叫做Fractionally Strided Convolution(小數步長的卷積)。對於步長 s>1的卷積,我們可能會想到其對應的反卷積步長 s′<1。

我們可以理解為:在其輸入特征單元之間插入 s?1 個0,插入0後把其看出是新的特征輸入。

技術分享圖片

FCN中的使用

在FCN的原文中提到deconvolutional layer中的kernel是可以被訓練的,也可以是固定的,即默認的二維bilinear kernel。
之所以說FCN中的反卷積操作不是原則意義上transposed convolution,是因為作者設置其中的學習率lr_mult為0,沒有讓該層學習。即卷積核是固定不變的。?

layer {
  name: "upscore"
  type: "Deconvolution"
  bottom: "score_fr"
  top: "upscore"
  param {
    lr_mult: 0
  }
  convolution_param {
    num_output: 21
    bias_term: false
    kernel_size: 64
    stride: 32
  }
}

TF中的使用

上采樣利用的是conv2d_transpose函數,將輸入特征插值到一個更大的特征圖然後進行卷積。

conv2d_transpose(value,filter,output_shape,strides,padding..)
Args:
value: A 4-D `Tensor` of type `float` and shape
`[batch, height, width, in_channels]` for `NHWC` data format or `[batch, in_channels, height, width]` for `NCHW` data format.
filter: A 4-D `Tensor` with the same type as `value` and shape `[height, width, output_channels, in_channels]`. `filter`'s `in_channels` dimension must match that of `value`.
output_shape: A 1-D `Tensor` representing the output shape of the deconvolution op.
strides: A list of ints. The stride of the sliding window for each dimension of the input tensor.
padding: A string, either `'VALID'` or `'SAME'`. The padding algorithm.

好了,回到我們要研究的問題
反向傳播、反卷積、導向反向傳播的區別在於反向傳播過程中經過ReLU層時對梯度的不同處理策略。在論文中有詳細描述。

技術分享圖片

雖然過程上的區別看起來沒有非常微小,但是在最終的效果上卻有很大差別。

技術分享圖片

使用普通的反向傳播得到的圖像噪聲較多,基本看不出模型的學到了什麽東西。使用反卷積可以大概看清楚貓和狗的輪廓,但是有大量噪聲在物體以外的位置上。導向反向傳播基本上沒有噪聲,特征很明顯的集中貓和狗的身體部位上。

雖然借助反卷積和導向反向傳播我們“看到”了CNN模型神秘的內部,但是卻並不能拿來解釋分類的結果,因為它們對類別並不敏感,直接把所有能提取的特征都展示出來了。在剛才的圖片中,模型給出的分類結果是貓,但是通過反卷積和導向反向傳播展示出來的結果卻同時包括了狗的輪廓。換句話說,我們並不知道模型到底是通過哪塊區域判斷出當前圖片是一只貓的。要解決這個問題,我們必須考慮其他辦法。

CAM

大家在電視上應該都看過熱成像儀生成的圖像

技術分享圖片

圖像中動物或人因為散發出熱量,所以能夠清楚的被看到。接下來要介紹的CAM(Class Activation Mapping)產生的CAM圖與之類似,當我們需要模型解釋其分類的原因時,它以熱力圖(Saliency Map,我不知道怎麽翻譯最適合,叫熱力圖比較直觀一點)的形式展示它的決策依據,如同在黑夜中告訴我們哪有發熱的物體。

對一個深層的卷積神經網絡而言,通過多次卷積和池化以後,它的最後一層卷積層包含了最豐富的空間和語義信息,再往下就是全連接層和softmax層了,其中所包含的信息都是人類難以理解的,很難以可視化的方式展示出來。所以說,要讓卷積神經網絡的對其分類結果給出一個合理解釋,必須要充分利用好最後一個卷積層。

技術分享圖片

CAM利用GAP(Global Average Pooling)替換掉了全連接層。可以把GAP視為一個特殊的average pool層,只不過其pool size和整個特征圖一樣大,其實說白了就是求每張特征圖所有像素的均值.

技術分享圖片

GAP的優點在NIN的論文中說的很明確了:由於沒有了全連接層,輸入就不用固定大小了,因此可支持任意大小的輸入;此外,引入GAP更充分的利用了空間信息,且沒有了全連接層的各種參數,魯棒性強,也不容易產生過擬合;

還有很重要的一點是,在最後的 mlpconv層(也就是最後一層卷積層)強制生成了和目標類別數量一致的特征圖,經過GAP以後再通過softmax層得到結果,這樣做就給每個特征圖賦予了很明確的意義,也就是categories confidence maps。

如果你當時不理解這個categories confidence maps是個什麽東西,結合CAM應該就能很快理解。

我們重點看下經過GAP之後與輸出層的連接關系(暫不考慮softmax層),實質上也是就是個全連接層,只不過沒有了偏置項,如圖所示:

技術分享圖片

對每一個類別C,每個特征圖k的均值都有一個對應的w,記為\(w^c_k\)

CAM的基本結構就是這樣了,下面就是和普通的CNN模型一樣訓練就可以了。訓練完成後才是重頭戲:我們如何得到一個用於解釋分類結果的熱力圖呢?其實非常簡單,比如說我們要解釋為什麽分類的結果是羊駝,我們把羊駝這個類別對應的所有\(w^c_k\)取出來,求出它們與自己對應的特征圖的加權和即可。由於這個結果的大小和特征圖是一致的,我們需要對它進行上采樣,疊加到原圖上去,如下所示。

技術分享圖片

CAM以熱力圖的形式告訴了我們,模型是重點通過哪些像素確定這個圖片是羊駝了。

Grad-CAM方法

前面看到CAM的解釋效果已經很不錯了,但是它有一個致使傷,就是它要求修改原模型的結構,導致需要重新訓練該模型,這大大限制了它的使用場景。如果模型已經上線了,或著訓練的成本非常高,我們幾乎是不可能為了它重新訓練的。於是乎,Grad-CAM橫空出世,解決了這個問題。

Grad-CAM的基本思路和CAM是一致的,也是通過得到每對特征圖對應的權重,最後求一個加權和
但是它與CAM的主要區別在於求權重\(w^c_k\)的過程。CAM通過替換全連接層為GAP層,重新訓練得到權重,而Grad-CAM另辟蹊徑,用梯度的全局平均來計算權重。事實上,經過嚴格的數學推導,Grad-CAM與CAM計算出來的權重是等價的。為了和CAM的權重做區分,定義Grad-CAM中第k個特征圖對類別c的權重為\(α^c_k\),可通過下面的公式計算:

\[\alpha_k^c=\frac{1}{Z}\sum\limits_{i}\sum\limits_{j}\frac{\partial y^c}{\partial A_{ij}^k}\]

其中,Z為特征圖的像素個數,\(y^c\)是對應類別c的分數(在代碼中一般用logits表示,是輸入softmax層之前的值),\(A^k_{ij}\)表示第k個特征圖中,(i,j)位置處的像素值。求得類別對所有特征圖的權重後,求其加權和就可以得到熱力圖。

\[L_{Grad-CAM}^c=ReLU(\sum\limits_k\alpha_k^cA^k)\]

整體結構如下圖所示

技術分享圖片

註意這裏和CAM的另一個區別是,Grad-CAM對最終的加權和加了一個ReLU,加這麽一層ReLU的原因在於我們只關心對類別c有正影響的那些像素點,如果不加ReLU層,最終可能會帶入一些屬於其它類別的像素,從而影響解釋的效果。使用Grad-CAM對分類結果進行解釋的效果如下圖所示:

技術分享圖片

除了直接生成熱力圖對分類結果進行解釋,Grad-CAM還可以與其他經典的模型解釋方法如導向反向傳播相結合,得到更細致的解釋。

技術分享圖片

這樣就很好的解決了反卷積和導向反向傳播對類別不敏感的問題。當然,Grad-CAM的神奇之處還不僅僅局限在對圖片分類的解釋上,任何與圖像相關的深度學習任務,只要用到了CNN,就可以用Grad-CAM進行解釋,如圖像描述(Image Captioning),視覺問答(Visual Question Answering)等,所需要做的只不過是把yc換為對應模型中的那個值即可。

限於篇幅,本文就不展開了,更多細節,強烈建議大家去讀讀論文,包括Grad-CAM與CAM權重等價的證明也在論文中。如果你只是想在自己的模型中使用Grad-CAM,可以參考這個鏈接,熟悉tensorflow的話實現起來真的非常簡單,一看就明白。

LIME

前面共同的局限性:當模型對我們來說完全為一個黑盒時就無能為力了。針對這個問題,這裏介紹另一套辦法,即使我們對模型一無所知也能夠對它的行為作出解釋。

LIME是KDD 2016上一篇非常漂亮的論文,思路簡潔明了,適用性廣,理論上可以解釋任何分類器給出的結果。其核心思想是:對一個復雜的分類模型(黑盒),在局部擬合出一個簡單的可解釋模型,例如線性模型、決策樹等等。這樣說比較籠統,我們從論文中的一張示例圖來解釋:

技術分享圖片

如圖所示,紅色和藍色區域表示一個復雜的分類模型(黑盒),圖中加粗的紅色十字表示需要解釋的樣本,顯然,我們很難從全局用一個可解釋的模型(例如線性模型)去逼近擬合它。

但是,當我們把關註點從全局放到局部時,可以看到在某些局部是可以用線性模型去擬合的。具體來說,我們從加粗的紅色十字樣本周圍采樣,所謂采樣就是對原始樣本的特征做一些擾動,將采樣出的樣本用分類模型分類並得到結果(紅十字和藍色點),同時根據采樣樣本與加粗紅十字的距離賦予權重(權重以標誌的大小表示)。虛線表示通過這些采樣樣本學到的局部可解釋模型,在這個例子中就是一個簡單的線性分類器。在此基礎上,我們就可以依據這個局部的可解釋模型對這個分類結果進行解釋了。

一個看似復雜的模型通過我們巧妙的轉換,就能夠從局部上得到一個讓人類理解的解釋模型,光這樣說還是顯得有些空洞,具體來看看LIME在圖像識別上的應用。我們希望LIME最好能生成和Grad-CAM一樣的熱力圖解釋。但是由於LIME不介入模型的內部,需要不斷的擾動樣本特征,這裏所謂的樣本特征就是指圖片中一個一個的像素了。仔細一想就知道存在一個問題,LIME采樣的特征空間太大的話,效率會非常低,而一張普通圖片的像素少說也有上萬個。若直接把每個像素視為一個特征,采樣的空間過於龐大,嚴重影響效率;如果少采樣一些,最終效果又會比較差。

所以針對圖像任務使用LIME時還需要一些特別的技巧,也就是考慮圖像的空間相關和連續的特性。不考慮一些極小特例的情況下,圖片中的物體一般都是由一個或幾個連續的像素塊構成,所謂像素塊是指具有相似紋理、顏色、亮度等特征的相鄰像素構成的有一定視覺意義的不規則像素塊,我們稱之為超像素。相應的,將圖片分割成一個個超像素的算法稱為超像素分割算法,比較典型的有SLIC超像素分割算法還有quickshit等,這些算法在scikit-image庫中都已經實現好了,quickshit分割後如圖所示:

技術分享圖片

從特征的角度考慮,實際上就不再以單個像素為特征,而是以超像素為特征,整個圖片的特征空間就小了很多,采樣的過程也變的簡單了許多。更具體的說,圖像上的采樣過程就是隨機保留一部分超像素,隱藏另一部分超像素,如下所示:

技術分享圖片

從圖中可以很直觀的看出這麽做的意義:找出對分類結果影響最大的幾個超像素,也就是說模型僅通過這幾個像素塊就已經能夠自信的做出預測。這裏還涉及到一個特征選擇的問題,畢竟我們不可能窮舉特征空間所有可能的樣本,所以需要在有限個樣本中找出那些關鍵的超像素塊。雖然這部分沒有在論文中過多提及,但在LIME的代碼實現中是一個重要部分,實現了前向搜索(forward selection)、Lasso和嶺回歸(ridge regression)等特征選擇方式,默認當特征數小於等於6時采用前向搜索,其他情況采用嶺回歸。

整體流程如圖:

技術分享圖片

和Grad-CAM一樣,LIME同樣可以對其他可能的分類結果進行解釋。

技術分享圖片

LIME除了能夠對圖像的分類結果進行解釋外,還可以應用到自然語言處理的相關任務中,如主題分類、詞性標註等。因為LIME本身的出發點就是模型無關的,具有廣泛的適用性。

雖然LIME方法雖然有著很強的通用性,效果也挺好,但是在速度上卻遠遠不如Grad-CAM那些方法來的快。當然這也是可以理解的,畢竟LIME在采樣完成後,每張采樣出來的圖片都要通過原模型預測一次結果。

說來也巧,在寫這篇文章的時候,AAAI 2018的論文放出來了,其中有LIME作者的最新研究成果Anchors,順道去了解了一下。Anchors指的是復雜模型在局部所呈現出來的很強的規則性的規律,註意和LIME的區別,LIME是在局部建立一個可理解的線性可分模型,而Anchors的目的是建立一套更精細的規則系統。不過看過論文以後感覺更多是在和文本相關的任務上有不錯的表現,在圖像相關的任務上並沒有什麽特別另人耳目一新的東西,只是說明了在Anchor(圖像中指若幹個超像素)固定的情況下,其他像素無論替換為什麽,現有的模型都會罔顧人類常識,自信的做出錯誤判斷。這部分內容由於前幾年看多了Adversarial Samples,已經見怪不怪了。

小結

實際上在模型可解釋性這塊還有其他很多相關研究,包括最近的AAAI 2018上也有幾篇這方面的文章,如Beyond Sparsity: Tree Regularization of Deep Models for Interpretability,這都在一定程度上說明,業內還是重視這個方向的。尤其在涉及到醫療、自動駕駛等人命關天的應用場合,可解釋性顯得尤為重要。

憑什麽相信你,我的CNN模型