前言:這只是我的一個學(xué)習(xí)筆記,里邊肯定有不少錯誤,還希望有大神能幫幫找找,由于是從小白的視角來看問題的,所以對于初學(xué)者或多或少會有點(diǎn)幫助吧。 1:人工全連接神經(jīng)網(wǎng)絡(luò)和BP算法 <1>:人工神經(jīng)網(wǎng)絡(luò)結(jié)構(gòu)與人工神經(jīng)網(wǎng)絡(luò)可以完美分割任意數(shù)據(jù)的原理: 本節(jié)圖片來源于斯坦福Andrew Ng老師coursea課件(此大神不多介紹,大家都懂) 在說明神經(jīng)網(wǎng)絡(luò)之前,先介紹一下神經(jīng)網(wǎng)絡(luò)的基礎(chǔ)計(jì)算單元,感知器。 上圖就是一個簡單的感知器,藍(lán)色是輸入的樣本,g(z)是激活函數(shù),z=x1*w1+…,a=g(z) 這個東西可以用來干什么呢?我們可以令b=-30,w1=20,w2=20,此時限制輸入的x1和x2為0或者1,激活函數(shù)為sigmoid函數(shù): 上圖為sigmoid函數(shù)圖像,可以看出當(dāng)x很大時,此函數(shù)趨于1,當(dāng)x很小時,此函數(shù)趨于0,寫出真值表,可以發(fā)現(xiàn)這個感知器完成了一個邏輯與的操作。
將參數(shù)修改為b=-10,w1=20,w2=20,此時感知器又完成了一個邏輯或的操作,真值表就不寫了,也就是說改變這些圓圈圈之間的傳遞參數(shù),可以使這個感知器完成邏輯或和邏輯與的操作。當(dāng)然對一個輸入取非也不會有問題(b=10,w1=-20)。 因此,我們可以改變連接參數(shù),從而使感知器完成與、或、非的操作。而將兩層感知器連接起來,不就可以完成或非、與非、異或等操作了唄。 舉一個例子,比如讓一個神經(jīng)網(wǎng)絡(luò)分割下圖圓圈和×: 這里重新將邏輯或和邏輯與畫成類似上圖的格式: 而我們要達(dá)到的目標(biāo)則為: 所以想要分割這兩組點(diǎn),第一層求一次或得到一個神經(jīng)元,再求一個與得到另一個神經(jīng)元,第二層求與就能得到上圖結(jié)果了: 神經(jīng)網(wǎng)絡(luò)就是這樣分割一個普通線性分類器很難分割的區(qū)域的 當(dāng)神經(jīng)元和神經(jīng)網(wǎng)絡(luò)的層數(shù)更高的時候,區(qū)分下面的數(shù)據(jù)也就不是什么問題了: <2>:神經(jīng)網(wǎng)絡(luò)的結(jié)構(gòu)和前向運(yùn)算: 上圖是Andrew Ng老師課程中的截圖,這就是一個典型的神經(jīng)網(wǎng)絡(luò),我們設(shè)為j層到j(luò)+1層的傳遞矩陣,從輸入層(藍(lán)色)到中間的第二層,就有:
同理,第二層到輸出層:
注意這個神經(jīng)網(wǎng)絡(luò)的輸出只有一個值而神經(jīng)網(wǎng)絡(luò)的輸出可以有任意個,這里僅以此為例不再展開寫,上邊就是當(dāng)已知每一層之間的系數(shù)矩陣時,神經(jīng)網(wǎng)絡(luò)求解的過程。 只要我們可以通過某種訓(xùn)練手段的得到神經(jīng)網(wǎng)絡(luò)各層之間的系數(shù)矩陣,那么神經(jīng)網(wǎng)絡(luò)就可以用來完成機(jī)器學(xué)習(xí)任務(wù)了。 從這里開始,將通過一個例子來說明,感覺這樣子可以描述的更清楚些吧??赡芤彩菓?yīng)為我比較笨。。。 我們假設(shè)有m=500張樣本圖片,每個圖片的分辨率是3*3而且都是黑白的,圖片的label(標(biāo)簽)有3類,分別是烤雞、烤鴨和烤全羊。我們構(gòu)建一個雙隱層的神經(jīng)網(wǎng)絡(luò)來判斷任意一個輸入的3*3圖片是什么東西。這個神經(jīng)網(wǎng)絡(luò)只用來舉例,一個9像素的圖片當(dāng)然什么實(shí)際的意義了。。。 這個神經(jīng)網(wǎng)絡(luò)的結(jié)構(gòu)就是下邊這個樣子了: 輸入層是9個像素點(diǎn)的灰度值組成的向量X,有m=500個樣本,所以dim(X)=500*9,中間兩個隱層我們假設(shè)它們各有14個節(jié)點(diǎn), 一個隱層(hidden layer),=500*14,層是第二個隱層,=500*14,output就是輸出層,有3個類別分別表示雞,鴨,羊。維度當(dāng)然是500*3了,參數(shù)W的維度分別是9*14,9*14,b則是一個500*14,500*14的矩陣,但b的每一行都是一樣的,=>符號表示全連接,如果徹底畫出來是這個樣子的(懶得用visio畫了,沒啥意義) 對于bias項(xiàng)b,還可以這樣理解:在每一層中加一個節(jié)點(diǎn),這個節(jié)點(diǎn)固定值為1,從這個節(jié)點(diǎn)映射到下一層的每一個節(jié)點(diǎn)的參數(shù)組成的向量就是參數(shù)b,對于500個樣本,就是每一個樣本行都加上這個bias項(xiàng)了。 在numpy中,這么操作: z1 = X.dot(W1) + b1 #這里b1是1*14的 a1 = np.tanh(z1) #激活函數(shù)還有tanh、ReLU等等 z2 = a1.dot(W2) + b2 … X*W1出來是500*14,在numpy中加b1(1*14)就是在X*W1的每一行都加b1,同理,如果加某個500*1的向量,是每一列都加這個向量。這么設(shè)計(jì)有點(diǎn)困惑呢。。。數(shù)學(xué)老師說矩陣加法維度不一致不讓加的。 計(jì)算假設(shè)函數(shù)的公式就是下邊這樣:
這樣,對于這500個樣本,每個樣本的每一類的得分就都計(jì)算出來了。當(dāng)然由于參數(shù)組是隨機(jī)搞到的,得分不一定合理,比如一個標(biāo)簽是烤鴨的樣本,烤鴨的得分反而是最低的,這都有可能,想要定性的衡量這套參數(shù)的靠譜程度,從而優(yōu)化這套參數(shù),就要介紹下一個工具,損失函數(shù)了。 <3>:損失函數(shù)(cost function),判斷當(dāng)前這套參數(shù)的性能: 損失函數(shù)是干啥的呢,在這個例子中我們有m個樣本,然后我們隨便搞一套參數(shù)組合,把這m個樣本分別扔到神經(jīng)網(wǎng)絡(luò)中去運(yùn)算出輸出,由于我們知道這些樣本的標(biāo)簽,所以就可以判斷我們之前隨便搞的這套參數(shù)組合能不能用來求解未知的數(shù)據(jù),比如有一枚數(shù)據(jù)的標(biāo)簽是烤鴨,將這個數(shù)據(jù)扔到神經(jīng)網(wǎng)絡(luò)里,算出來的得分是: 烤鴨:2分,燒雞:12分,烤全羊:-78分 很明顯嘛,這套參數(shù)得到的值不對,按照神經(jīng)網(wǎng)絡(luò)的值不就把鴨子認(rèn)成雞了嘛。損失函數(shù)就是衡量這個不對的程度的函數(shù),顧名思義嘛,損失函數(shù)的值越小,說明你這套參數(shù)就越靠譜,越能表達(dá)樣本總體的特征。 在Andrew Ng課程中,老師直接給出了損失函數(shù):
K means the number of output units. L means total number of layers in the network. means number of units in layer l(not counting bias unit). m是樣本數(shù)量. 這個損失函數(shù)其實(shí)是一個logistic regression問題的交叉熵?fù)p失(cross entropy loss),一步一步來看這個損失是怎么來的哈,比較復(fù)雜。我舉的這個栗子是softmax回歸問題,就是多分類問題。 第一步是對輸出進(jìn)行歸一化處理(normalize),我們可以將得分轉(zhuǎn)換成概率形式,假設(shè)某個標(biāo)簽為烤鴨的樣本得分是: 烤鴨:2分,燒雞:12分,烤全羊:-78分 歸一化為: 烤鴨: 燒雞: 烤全羊: 這樣,輸出的樣本得分就變成了: 烤鴨:4.5*10^-5,燒雞:幾乎是1,烤全羊:8.2*10-40 這樣子就可以很方便的和樣本標(biāo)簽做比較了,比如這個樣本的標(biāo)簽是烤鴨,標(biāo)簽向量y就是[1,0,0]了。不是的話需要轉(zhuǎn)換成這種形式。 交叉熵?fù)p失,就是將這些概率和標(biāo)簽中正確的概率向量的差加起來再求一個負(fù)對數(shù),剛剛的數(shù)據(jù)比較龐大,我們假設(shè)計(jì)算得到的輸出概率向量為[0.1,0.5,0.4],這個意思就是神經(jīng)網(wǎng)絡(luò)認(rèn)為你輸入的這張圖片有0.1的概率是烤鴨,0.5的概率是燒雞…,但實(shí)際輸入的樣本圖片的標(biāo)簽是烤鴨,也就是[1,0,0]。那么他在每一個類別上的損失就是[1-0.1,0.5-0,0.4-0] 而cross entropy loss就等于
現(xiàn)在再感受一下這個式子?;腥淮笪虬?。如果這個類別標(biāo)簽是0,說明你輸出的softmax概率全部是損失,如果這個類標(biāo)簽是1,你輸出的概率本該是1,但差了1-p那么多,所以損失就是1-p。
K means the number of output units. L means total number of layers in the network. means number of units in layer l(not counting bias unit). 恩我是應(yīng)為笨才說的這么清楚的。。。 至于為毛叫交叉熵?fù)p失。。等我學(xué)完信息論再回答吧,留個坑。 有了損失函數(shù)的定義后,我們可以隨機(jī)初始化一組系數(shù)矩陣,然后使用梯度下降的方法找到一組(使用大量的樣本)令損失函數(shù)最小的系數(shù)矩陣,這就是SGD(隨機(jī)梯度下降) <4>:BP與SGD: 在介紹SGD算法之前,先簡單說一下什么是梯度下降(gradient descent)。我們假設(shè)有一個凸函數(shù)如圖所示,如何從隨機(jī)的一點(diǎn)逐漸收斂到這個函數(shù)的最小值呢? 下邊的偽代碼就是梯度下降。當(dāng)循環(huán)次數(shù)達(dá)到一定數(shù)量時,此時的x就非常接近f(x)的最小值了。 Repeat until convergence{
x=x- } a是一個更新率,當(dāng)a很小時梯度收斂的很慢,當(dāng)a較大時梯度收斂的較快,當(dāng)a過大時可能無法收斂,比如x減去一個很小的負(fù)值,函數(shù)值比原來距離正確的最小值點(diǎn)更遠(yuǎn)了??梢妼τ谶@樣一個平滑的凸函數(shù),迭代的步子會隨著次數(shù)增加越邁越小,原因就是導(dǎo)數(shù)越來越小了。這樣就會使得x逐漸逼近最小值點(diǎn)。 對于神經(jīng)網(wǎng)絡(luò)的cost function,它不僅僅有一個參數(shù),我們便需要求出cost function對每個參數(shù)的偏導(dǎo)數(shù),在最后統(tǒng)一進(jìn)行參數(shù)更新后進(jìn)行下一輪迭代。 神經(jīng)網(wǎng)絡(luò)系統(tǒng)使用正向傳播求當(dāng)前參數(shù)的損失,然后反向傳播回傳誤差,根據(jù)誤差信號迭代修正每層的權(quán)重。SGD算法(stochastic gradient descent)的第一步是隨機(jī)初始化每一個參數(shù)。Stochastic的意思正是隨機(jī)。通過這組隨機(jī)的參數(shù)計(jì)算得到每一個神經(jīng)元的輸入輸出值和損失函數(shù)后,就可以求損失函數(shù)對各個參數(shù)的偏導(dǎo)數(shù)了,梯度更新的那個delta就等于alpha*偏導(dǎo)數(shù)。偏導(dǎo)數(shù)怎么求就不多說了,高中數(shù)學(xué)嘍。 而BP算法則是用來求那一堆偏導(dǎo)數(shù)的,BP的意思是反向傳播。就是把最后一層的誤差反向傳遞回別的神經(jīng)元,得到每一層的誤差函數(shù),從而解出偏導(dǎo)數(shù)。 我們定義為第l層,節(jié)點(diǎn)j的誤差 對于輸出層(第四層) ,這里當(dāng)然每一個都是3維的向量 往前傳遞:
則損失函數(shù)對于每個參數(shù)的偏導(dǎo)數(shù)為:
這個東西的證明出奇的復(fù)雜,有興趣的可以谷歌一下,當(dāng)每一個偏導(dǎo)數(shù)都求出來后,就可以套用上邊的梯度下降算法迭代出來最佳的參數(shù)組合嘍。這就是神經(jīng)網(wǎng)絡(luò)。 好了,上邊的例子就是一個圖像分類的問題demo,差不多說的很清楚了吧。然后考慮一下實(shí)際的圖像分類問題,會遇到哪些問題呢? 首先圖像的分辨率不能是9像素了,這能看出來啥啊,然后就是圖像的類別,也不能就3類了,這個新球上的圖片還是有個幾千個類別的吧,這樣就會遇到一些計(jì)算上的問題,比如圖片的分辨率是1080p,那么輸入維度就是1980*1200=2376000,通常隱層節(jié)點(diǎn)數(shù)量要大于輸入維度,而隱層層數(shù)也隨著分類問題的復(fù)雜而提高,就算一個圖像分類神經(jīng)網(wǎng)絡(luò)的隱層節(jié)點(diǎn)數(shù)量和輸入維度一致,那傳遞參數(shù)W維度就成了。。。200w*200w=2萬億個了。。。這么大的數(shù)據(jù)量,老黃也沒轍,只能優(yōu)化算法。 關(guān)于深度的神經(jīng)網(wǎng)絡(luò)為何難以訓(xùn)練有很多細(xì)節(jié),可以推薦一本在線書: http:///chap5.html #我還沒看完。。 寫到這里深刻感覺到關(guān)于深度神經(jīng)網(wǎng)絡(luò)的知識量還是很大的,這里只做知識結(jié)構(gòu)梳理和重要的key point描述。其實(shí)對于此類知識,我個人的看法是掌握原理即可move on,需要其中的細(xì)節(jié)再去查看資料,對每一個細(xì)節(jié)都詳細(xì)證明是有一些浪費(fèi)時間的,對于初學(xué)者(just like me)來說,很快的了解并將這個技術(shù)應(yīng)用到一個測試平臺上是更重要的,其次是緊跟潮流看看最新的進(jìn)展是在研究什么。數(shù)學(xué)很重要,但它只是工具罷了。我們要掌握的是如何用數(shù)學(xué)解決問題。 具體怎么搞? 卷積神經(jīng)網(wǎng)絡(luò) |
|