當前位置:
首頁 > 科技 > 資源 | 來自獨秀同學的深度網路數學筆記,還不快收藏?

資源 | 來自獨秀同學的深度網路數學筆記,還不快收藏?


選自

towardsdatascience


作者:Piotr Skalski


機器之心編譯


參與:Geek AI、張倩






為了更加深入地了解深度網路背後的工作原理,本文作者花時間學習了隱藏在模型背後的數學原理,並對一些概念進行了梳理,包括神經網路、單個神經元、激活函數、損失函數等基本概念。本文敘述比較容易理解,數學基礎一般的讀者也能有所收穫。




如今,我們已經擁有了許多高級的、專業的神經網路程序庫和框架,例如:Keras、TensorFlow 或 Pytorch。我們不需要時刻擔心權值矩陣的規模,也不需要記住我們決定使用的激活函數的導數公式。通常,我們所需要做的就是創建一個神經網路。即使是一個結構非常複雜的網路,也只需要導入少量程序包和幾行代碼就能實現。這節省了我們查找漏洞的時間,提高了工作效率。然而,關於神經網路內部工作原理的知識對架構選擇、超參數調優以及優化等任務有很大幫助。



引言




為了更加深入地了解神經網路的工作原理,我決定在這個夏天花一些時間看一看隱藏在模型背後的數學原理。我還決定寫一篇文章將新學到的信息組織起來,幫助自己和他人理解這些難以理解的概念。對於那些對代數或微積分不太熟悉的人,我會盡量敘述地容易理解一些。正如標題所示,本文涉及到很多數學知識。





圖 1. 訓練集的可視化




舉例而言,我們將解決如上面圖 1 所示的數據集的二分類問題。從屬於這兩種類別的點形成了圓圈,這種數據的組織形式對於很多傳統機器學習演算法來說很不方便,但是一個小型神經網路卻可能利用這種數據很好地工作。為了解決這個問題,我們將使用具有圖 2 所示的結構的神經網路——五個全連接層,每層的節點數不一。我們將在隱藏層中使用 ReLU 作為激活函數,在輸出層中則使用 Sigmoid 函數。這是一個十分簡單的網路架構,但其複雜程度已經足以幫助我們應對上述問題。





圖 2. 神經網路架構





Keras 的解決方案




首先,我將展示使用目前最流行的機器學習庫之一——Keras 實現的解決方案。




from

 keras.models 

import

 Sequential

from

 keras.layers 

import

 Dense

model = Sequential()
model.add(Dense(

4

, input_dim=

2

,activation=

"relu"

))
model.add(Dense(

6

, activation=

"relu"

))
model.add(Dense(

6

, activation=

"relu"

))
model.add(Dense(

4

, activation=

"relu"

))
model.add(Dense(

1

, activation=

"sigmoid"

))

model.compile(loss=

"binary_crossentropy"

, optimizer=

"adam"

, metrics=[

"accuracy"

])
model.fit(X_train, y_train, epochs=

50

, verbose=

0

)



解決方案就是如此。正如我在引言中提到的,我們只需要引入少量的程序包、寫上幾行代碼就足以創建並訓練一個模型,該模型能夠以接近 100% 的準確率對我們測試集中的數據進行分類。我們的任務可以歸結為根據選定的網路架構提供超參數(網路層數、每一層中神經元的數量、激活函數或 epoch 的數量)。現在讓我們看看表面的框架背後發生了什麼。而且,為了防止你打瞌睡,我為學習過程創建了一個很酷的可視化演示樣例。




圖 3. 在訓練過程中,從屬於某一類別的區域的可視化過程




什麼是神經網路?




讓我們首先回答一個關鍵的問題:什麼是神經網路?這是一種受到生物學啟發而構建能夠進行學習並且獨立找出數據之間聯繫的計算機程序的方法。如圖 2 所示,網路就是一個以層次的形式組織起來的軟體「神經元」的集合,神經元以一種可以進行通信的方式連接起來。




單個神經元




每個神經元接受一組 x 值(從 x_1 到 x_n)作為輸入,然後計算出預測的 y^ 值。向量 *x *實際上包含訓練集的 m 個樣本中某個樣本的特徵值。此外,每個神經元都有一套自己的參數,這些參數通常指的是 w(權值的列向量)以及 b(偏置),在學習過程中參數會不斷變化。在每一輪迭代中,神經元會根據目前的權值向量 w 加上偏置計算出 x 向量值的加權平均。最後,計算結果會被傳遞給一個非線性的激活函數 g。在本文後面的部分,我將稍微提到一些目前最流行的激活函數。







圖 4. 單個神經元




單個網路層




現在,讓我們考慮稍微大一點的結構,看看如何對神經網路中的某一整層進行計算。我們將利用我們對於單個神經元中計算過程的知識,並且對整個層進行向量化,從而將這些計算組合成矩陣方程。為了統一符號,我們為選定的層「l」寫出這些方程。此外,下標 i 表示某神經元在這一層中的序號。





圖 5. 單個網路層




請注意:我們使用 *x *和 y^ 書寫單個神經元的方程,它們分別表示特徵的列向量以及預測值。當我們轉而對每一層的計算進行表示時,我們使用向量 *a *代表這一層的激活結果。因此,向量 *x *是第 0 層(輸入層)的激活結果。層中的每個神經元將根據以下方程進行類似的計算:







為了讓讀者更清晰地理解,我們將第二層的方程展開如下:







如你所見,在每一層中,我們都會執行許多非常相似的計算。使用「for 循環」執行這種計算的效率並不高,所以我們在這裡使用向量化處理來加速計算過程。首先,我們通過將轉置後的權值 w 的水平向量重疊起來得到矩陣 *W*。類似地,我們將層中的每個神經元的偏置重疊起來去創建垂直向量 *b*。現在,我們就可以一次性地直接為層中的所有神經元執行計算過程。我們同時會在下面寫出用到的矩陣和向量的維度。















對多個樣本進行向量化




目前我們看到的方程都只涉及到一個樣本。但是在神經網路的學習過程中,你通常會用到包含超過百萬條樣本的巨型數據集。因此,我們接下來要進行對多個樣本的向量化操作。假如我們的數據集擁有 m 條樣本,每個樣本帶有 nx 個特徵。首先,我們將每層的垂直向量 x、a 、 z 列在一起,分別構成 X,A,Z 矩陣。接著,我們考慮這些新創建的矩陣,重寫之前列出的方程。










什麼是激活函數,為什麼我們需要它?




激活函數是神經網路的關鍵元素之一。如果沒有激活函數,神經網路就會成為一個線性函數的組合,那麼神經網路最終本身也就是一個線性函數。這樣一來,模型的擴展性就會非常有限,並不比 logistic 回歸模型強。而這種非線性元素讓模型具有很大的靈活性,也使我們能夠在學習過程中創建複雜的函數。激活函數也對訓練的速度有很大影響,這也是我們選擇激活函數的一個重要標準。圖 6 顯示了一些常用的激活函數。目前,對於隱藏層來說,ReLU 可能是最流行的激活函數。我們仍然會使用 sigmoid,尤其是當我們要處理二分類問題,希望模型的返回值介於 0-1 之間時,我們在輸出層會使用 sigmoid。





圖 6. 最流行的激活函數及其導數




損失函數




損失函數的值是關於學習過程的進度的基本信息來源。一般來說,損失函數用來衡量我們離「理想」的解還有多遠。在本文的例子中,我們使用的是對數損失函數(binary cross entropy),對於不同的問題,我們可以應用不同的激活函數。我們所使用的激活函數如下,而其函數值在學習過程中變化的可視化演示如圖 7 所示。我們可以看到,隨著一次次的迭代,損失函數的值是如何減小、而準確率是如何提升的。








圖 7. 學習過程中準確率和損失函數值的變化情況




神經網路是如何學習的?




神經網路的學習過程就是不斷改變參數 W 和 b 的值,從而使損失函數最小。為了實現這個目標,我們需要藉助於微積分知識,並且使用梯度下降法去找到函數的最小值。在每輪迭代中,我們將計算損失函數對我們的神經網路中每個參數的偏導數。對於那些不熟悉這類計算的人來說,我只能說導數具有很強的刻畫函數斜率的能力。多虧了這一點,我們就能知道如何操作這些變數,從而使函數值移動到圖中谷底的鞍點。為了讓你對梯度下降的工作方式形成直觀的印象(防止你再次睡著),我在下面製作了一個小的可視化演示樣例。可以看到,在每個連續的 epoch 中,我們是一步步朝著最小值移動的。在我們的神經網路中,它以相同的方式工作,在每輪迭代中計算出的梯度顯示了我們應該移動的方向。主要的區別在於,在我們的神經網路模型中,我們擁有更多需要操作的參數。那麼,應該如何計算如此複雜的導數呢?





圖 8. 梯度下降過程




反向傳播




反向傳播是一種可以幫我們計算出非常複雜的梯度的演算法。神經網路的參數將根據下面的公式進行調整:







在上面的方程中,α 代表學習率——一種讓你能夠控制執行調整的程度的超參數。選擇一個合適的學習率是十分關鍵的,如果學習率太小,神經網路的學習速度就會非常慢;而如果學習率太大,我們又可能找不到最小值。




dW 和 db 是使用鏈式法則計算出來的損失函數關於 W 和 b 的偏導數。dW 和 db 的規模分別與 W 和 b 相同。圖 9 顯示了神經網路中的一連串操作。我們可以很清楚地看到前向傳播和後向傳播協同工作,從而優化損失函數。








圖 9. 前向傳播和後向傳播




結語




希望我已經為你解釋清楚了神經網路內部發生的數學運算過程。能夠對這個計算過程的基礎有最基本的了解將有助於我們使用神經網路。我認為我所提到的是這部分最重要的知識,但這也只是這些數學知識的冰山一角。我強烈建議你們試著編程實現一個這樣的小型神經網路,最好僅僅使用 Numpy,而不要使用高級框架。




原文鏈接:https://towardsdatascience.com/https-medium-com-piotr-skalski92-deep-dive-into-deep-networks-math-17660bc376ba






本文為機器之心編譯,

轉載請聯繫本公眾號獲得授權



?------------------------------------------------


加入機器之心(全職記者 / 實習生):hr@jiqizhixin.com


投稿或尋求報道:

content

@jiqizhixin.com


廣告 & 商務合作:bd@jiqizhixin.com

喜歡這篇文章嗎?立刻分享出去讓更多人知道吧!

本站內容充實豐富,博大精深,小編精選每日熱門資訊,隨時更新,點擊「搶先收到最新資訊」瀏覽吧!


請您繼續閱讀更多來自 機器之心 的精彩文章:

《頭號玩家》Oasis的混合現實版來了!Magic Leap面世
嘿嘿,想用 DanceNet 變成會跳舞的小哥哥或小姐姐嗎?超簡單!

TAG:機器之心 |