深度學習(二十二)Dropout淺層理解與實現

原文地址:http://blog.csdn.net/hjimce/article/details/50413257

作者:hjimce

一、相關工作

    本來今天是要搞《Maxout Networks》和《Network In Network》的,結果發現maxout和dropout有點類似,所以就對dropout做一下相關的總結,瞭解一下其代碼層面的實現。

    Dropout是2012年深度學習視覺領域的開山之作paper:《ImageNet Classification with Deep Convolutional》所提到的算法,用於防止過擬合。在我剛入門深度學習,搞視覺的時候,就有所耳聞,當時只知道它是爲了防止過擬合。記得以前啥也不懂,看到《ImageNet Classification with Deep Convolutional》的思路,然後看到很多文獻都是採用了同樣的思路,於是就跟着模仿,也不知道爲什麼要這麼設計,然後去kaggle競賽,感覺自己模仿設計出來的網絡,感覺精度都好爛,然後也不會分析網絡設計哪些合理,哪些不合理。當時要麼就是模仿別人,要麼就是直接用別人的網絡,被領導鄙視了一番……還是不囉嗦了,說多了都是淚。

    網上都說dropout是讓某些神經元以一定的概率不工作,但是具體代碼怎麼實現?原理又是什麼,還是有點迷糊,所以就大體掃描了文獻:《Improving neural networks by preventing co-adaptation of feature detectors》、《Improving Neural Networks with Dropout》、《Dropout: A Simple Way to Prevent Neural Networks from Overtting》,不過感覺看完以後,還是收穫不是很大。下面是我的學習筆記,因爲看的不是很細,也沒有深入理解,有些地方可能有錯,如有錯誤還請指出。

二、算法概述

我們知道如果要訓練一個大型的網絡,訓練數據很少的話,那麼很容易引起過擬合(也就是在測試集上的精度很低),可能我們會想到用L2正則化、或者減小網絡規模。然而深度學習領域大神Hinton,在2012年文獻:《Improving neural networks by preventing co-adaptation of feature detectors》提出了,在每次訓練的時候,讓一半的特徵檢測器停過工作,這樣可以提高網絡的泛化能力,Hinton又把它稱之爲dropout。

Hinton認爲過擬合,可以通過阻止某些特徵的協同作用來緩解。在每次訓練的時候,每個神經元有百分之50的機率被移除,這樣可以讓一個神經元的出現不應該依賴於另外一個神經元。

另外,我們可以把dropout理解爲 模型平均。 假設我們要實現一個圖片分類任務,我們設計出了100000個網絡,這100000個網絡,我們可以設計得各不相同,然後我們對這100000個網絡進行訓練,訓練完後我們採用平均的方法,進行預測,這樣肯定可以提高網絡的泛化能力,或者說可以防止過擬合,因爲這100000個網絡,它們各不相同,可以提高網絡的穩定性。而所謂的dropout我們可以這麼理解,這n個網絡,它們權值共享,並且具有相同的網絡層數(這樣可以大大減小計算量)。我們每次dropout後,網絡模型都可以看成是整個網絡的子網絡。(需要注意的是如果採用dropout,訓練時間大大延長,但是對測試階段沒影響)。

囉嗦了這麼多,那麼到底是怎麼實現的?Dropout說的簡單一點就是我們讓在前向傳導的時候,讓某個神經元的激活值以一定的概率p,讓其停止工作,示意圖如下:

 

左邊是原來的神經網絡,右邊是採用Dropout後的網絡。這個說是這麼說,但是具體代碼層面是怎麼實現的?怎麼讓某個神經元以一定的概率停止工作?這個我想很多人還不是很瞭解,代碼層面的實現方法,下面就講解一下其代碼層面的實現。以前我們網絡的計算公式是:

 

採用dropout後計算公式就變成了:

 

上面公式中Bernoulli函數,是爲了以概率p,隨機生成一個0、1的向量。

算法實現概述:

1、其實Dropout很容易實現,源碼只需要幾句話就可以搞定了,讓某個神經元以概率p,停止工作,其實就是讓它的激活值以概率p變爲0。比如我們某一層網絡神經元的個數爲1000個,其激活值爲x1,x2……x1000,我們dropout比率選擇0.4,那麼這一層神經元經過drop後,x1……x1000神經元其中會有大約400個的值被置爲0。

2、經過上面屏蔽掉某些神經元,使其激活值爲0以後,我們還需要對向量x1……x1000進行rescale,也就是乘以1/(1-p)。如果你在訓練的時候,經過置0後,沒有對x1……x1000進行rescale,那麼你在測試的時候,就需要對權重進行rescale:

問題來了,上面爲什麼經過dropout需要進行rescale?查找了相關的文獻,都沒找到比較合理的解釋,後面再結合源碼說一下我對這個的見解。

    所以在測試階段:如果你既不想在訓練的時候,對x進行放大,也不願意在測試的時候,對權重進行縮小(乘以概率p)。那麼你可以測試n次,這n次都採用了dropout,然後對預測結果取平均值,這樣當n趨近於無窮大的時候,就是我們需要的結果了(也就是說你可以採用train階段一模一樣的代碼,包含了dropout在裏面,然後前向傳導很多次,比如1000000次,然後對着1000000個結果取平均值)。

三、源碼實現

下面我引用keras的dropout實現源碼進行講解,keras開源項目github地址爲:

https://github.com/fchollet/keras/tree/master/keras。其dropout所在的文件爲:

https://github.com/fchollet/keras/blob/master/keras/backend/theano_backend.py,dropout實現函數如下:

#dropout函數的實現
def dropout(x, level):
    if level < 0. or level >= 1:#level是概率值,必須在0~1之間
        raise Exception('Dropout level must be in interval [0, 1[.')
    retain_prob = 1. - level
    #我們通過binomial函數,生成與x一樣的維數向量。binomial函數就像拋硬幣一樣,我們可以把每個神經元當做拋硬幣一樣
    #硬幣 正面的概率爲p,n表示每個神經元試驗的次數
    #因爲我們每個神經元只需要拋一次就可以了所以n=1,size參數是我們有多少個硬幣。
    sample=np.random.binomial(n=1,p=retain_prob,size=x.shape)#即將生成一個0、1分佈的向量,0表示這個神經元被屏蔽,不工作了,也就是dropout了
    print sample
    x *=sample#0、1與x相乘,我們就可以屏蔽某些神經元,讓它們的值變爲0
    print x
    x /= retain_prob
 
    return x
#對dropout的測試,大家可以跑一下上面的函數,瞭解一個輸入x向量,經過dropout的結果
x=np.asarray([1,2,3,4,5,6,7,8,9,10],dtype=np.float32)
dropout(x,0.4)</span>
函數中,x是本層網絡的激活值。Level就是dropout就是每個神經元要被丟棄的概率。不過對於dropout後,爲什麼需要進行rescale:


x /= retain_prob
有的人解釋有點像歸一化一樣,就是保證網絡的每一層在訓練階段和測試階段數據分佈相同。我查找了很多文獻,都沒找到比較合理的解釋,除了在文獻《Regularization of Neural Networks using DropConnect》稍微解釋了一下,其它好像都沒看到相關的理論解釋。

我們前面說過,其實Dropout是類似於平均網絡模型。我們可以這麼理解,我們在訓練階段訓練了1000個網絡,每個網絡生成的概率爲Pi,然後我們在測試階段的時候,我們肯定要把這1000個網絡的輸出結果都計算一遍,然後用這1000個輸出,乘以各自網絡的概率Pi,求得的期望值就是我們最後的平均結果。我們假設,網絡模型的輸出如下:

M是Dropout中所有的mask集合。所以當我們在測試階段的時候,我們就是對M中所有的元素網絡,最後所得到的輸出,做一個期望:

P(M)表示網絡各個子網絡出現的概率。因爲dropout過程中,所有的子網絡出現的概率都是相同的,所以。

個人總結:個人感覺除非是大型網絡,才採用dropout,不然我感覺自己在一些小型網絡上,訓練好像很是不爽。之前搞一個比較小的網絡,搞人臉特徵點定位的時候,因爲訓練數據不夠,怕過擬合,於是就採用dropout,最後感覺好像訓練速度好慢,從此就對dropout有了偏見,感覺訓練過程一直在波動,很是不爽。

參考文獻:

1、《Improving neural networks by preventing co-adaptation of feature detectors》

2、《Improving Neural Networks with Dropout》

3、《Dropout: A Simple Way to Prevent Neural Networks from Overtting》

4、《ImageNet Classification with Deep Convolutional》

**********************作者:hjimce   時間:2015.12.20  聯繫QQ:1393852684   原創文章,轉載請保留原文地址、作者等信息***************
--------------------- 
作者:hjimce 
來源:CSDN 
原文:https://blog.csdn.net/hjimce/article/details/50413257 
版權聲明:本文爲博主原創文章,轉載請附上博文鏈接!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章