大資料文摘作品
編譯 | 璐,高寧,樊恆巖,田奧
簡介
卷積神經網路聽起來像一個奇怪組合。這個名字涉及了生物學、數學,還有一點電腦科學亂入,但它卻是計算機視覺領域最具影響的創新。在2012年,由於Alex Krizhevsky使用神經網路贏得了ImageNet挑戰賽的冠軍(這個比賽可被看作計算機視覺領域的奧運會),神經網路第一次嶄露頭角。神經網路把分類誤差從26%降低到15%,這在當時是一個令人震驚的進步。
從那以後,大量公司在他們的核心業務中使用深度學習。Facebook把神經網路用在自動標籤演算法上,google把它用於相片搜尋,亞馬遜把它用於產品推薦,Pinterest把它用於房屋列表個性化,Instagram把它用於搜尋框架。
然而,神經網路經典且最常用的使用案例仍是影像處理。就讓我們一起來看看,CNN(卷積神經網路)是如何在影像處理任務中實現影像分類的。
問題描述
影像分類這項任務旨在把輸入的圖片分入某一特定類別(例如一隻貓或者狗等)或者可能性最大的類別。對我們人類而言,影像識別的能力是我們從出生起就在學習的一項任務,這項任務對於成年人來說更是不費吹灰之力。無需多想,我們就能迅速而準確地識別出我們所處的環境和我們周圍的物體。大多數時候,當我們看到圖片或者是周圍的世界時,甚至不用刻意觀察,我們就可以立刻描繪出場景的特徵,並給每個物體貼上標籤。這些迅速識別模式、歸納知識以及適應不同影像與環境的技能一直是機器難以擁有的。
輸入和輸出
當電腦看見一張影像(把影像作為輸入),它實際上看到的是一個由畫素值組成的陣列。基於解析度和影像的大小,它會看到一個32 x 32 x 3的陣列(3指的是RGB的值)。假設我們有一張JPG格式、大小為480 x 480的彩色圖片,那麼它對應的就是一個480 x 480 x 3的陣列。陣列中的每一個數字都是介於0到255之間的,這些數字代表畫素在這一點的強度。儘管這些數字對於人類做影像分類是毫無意義的,它們卻是電腦唯一能得到的輸入資訊。計算機識別影像的基本思路是,你把這個陣列輸入給電腦,它就會輸出一個數字,代表該影像屬於某一特定分類的機率(例如,80%的機率是貓,15%的機率是狗,5%的機率是鳥)。
計算機的任務
現在我們知道了問題所在,以及輸入和輸出,下面我們就該來思考一下怎麼完成這個過程了。我們希望計算機能夠區分開我們輸入的所有影像,並且識別出其獨特的特徵,比如哪些特徵是狗特有的,哪些是貓特有的。這個過程也會在我們的大腦中下意識地進行。當我們觀察狗的圖片時,我們會在圖片中尋找可識別的特徵,例如爪子或者4條腿,這樣我們就能將它正確地分類。同樣的,透過尋找例如邊緣和曲線之類的底層特徵,並透過一系列的卷積層建立一個更加抽象的概念,電腦也能進行影像分類。這是CNN工作原理的概覽。下面讓我們來了解一下它工作的細節。
與生物學的聯絡
首先,講一點背景知識。當你剛聽到卷積神經網路這一術語時,你可能會想到神經學或者生物學。沒錯,就是這樣!一定程度上,CNN確實從視覺皮層的生物學中汲取了靈感。視覺神經中有一個小分割槽中的細胞對特定視覺區域很敏感。這個想法是從Hubel和Wiesel在1962年做的一個有趣的實驗中擴充套件得來的。實驗顯示,大腦中的一些特別的神經細胞只會對特定方向的邊緣做出反應。例如,一些神經元在看到垂直的邊緣時會被激發,而另外一些則會被水平或者斜對角邊緣激發。Hubel和Wiesel發現所有這些神經元都排列在一個圓柱構架中,它們一起工作,產生視覺感知。系統中特定部件完成特定任務的想法(視覺皮層中的神經細胞尋找特定特徵)對機器也適用,它是CNN的基本原理。
結構
回到細節上來,CNN所需做的是,拿到影像,輸入一系列卷積、非線性、池化(下采樣)和完全連線的層中,最終得到一個輸出。就像我們之前說的,輸出可以是能最好描述圖的分類的一個單一結果或者一組分類的機率。現在,最難的部分即是理解每一層的工作原理。首先讓我們來看看最重要的部分。
第一層(數學部分)
CNN的第一層通常是卷積層。首先,你需要記住卷基層的輸入是什麼。如上所述,輸入是一個32 x 32 x 3的畫素值陣列。現在,解釋卷積層的最好的方法就是想象一個手電筒正從影像的左上角照過。我們假設這個手電筒的光覆蓋了一個5 x 5的區域。然後,我們想象這個手電筒的光照過輸入影像的所有區域。在機器學習的術語中,這個手電筒叫做過濾器(有時也被稱作神經元或者核心),手電筒照過的區域稱作感受域。現在這個過濾器也是一個陣列(其中的數字被稱為權重或者引數)。一個非常重要的注意事項是過濾器的深度要和輸入的深度相同(這保證可以進行數學運算),所以這個過濾器的大小是5 x 5 x 3。現在我們以濾器的第一個位置為例,即影像左上角。隨著過濾器在輸入影像上滑動,或者進行卷積運算,過濾器中的值會和影像上的原始值相乘(又稱作計算點積)。將這些乘積相加(從數學角度講,一共會有75個乘積),你就得到了一個數字。記住,這個數字只是過濾器在影像左上角時得到的結果。現在,我們在輸入內容的每一個位置重複這一過程。(下一步是把過濾器向右移動一個單位,然後再右移一個單位,以此類推)。輸入內容上的每一個特有位置都會產生一個值。過濾器滑過所有位置後,你會發現你得到了一個28 x 28 x 1的陣列,我們把它稱作啟用對映或特徵對映。你得到一個28 x 28陣列的原因是,5 x 5的過濾器在32 x 32的輸入影像上有784個不同的位置。這784個數字對映成了一個28 x 28的陣列。
(小注:包含上圖在內的本文的一些圖片,來自一本Michael Nielsen寫的《神經網路和深度學習》,強烈推薦。)
假設現在我們用兩個而非一個5 x 5 x 3的過濾器,那麼我們的輸出就變成了28 x 28 x 2的陣列。透過使用更多的過濾器,我們能更好的儲存空間維度。數學上講,這就是卷積層上發生的事。
第一層(任務概況)
讓我們從更高層次來看卷積實際在做什麼吧。每一個過濾器都可以看做為一個特徵標識器。這裡的特徵是指直線、簡單的顏色以及曲線之類的東西,這些都是圖片所共有的最簡單特徵。我們的第一個過濾器是一個7 x 7 x 3的曲線檢測器。(為了簡化這個問題,在這裡我們先忽略過濾器有3個單位深度這一事實,只考慮過濾器和圖片的最上層切片。)曲線檢測器有一定的畫素結構,在該結構中,沿著曲線形狀的區域將具有更高的數值。
圖片標題:左- 過濾器的畫素化表現
右-視覺化的曲線檢測過濾器
現在讓我們將這個數學問題視覺化。當我們對左上角的輸入使用這個過濾器時,這個區域的畫素值和過濾器將進行乘法運算。以下圖為例,我們將過濾器放在左上角。
圖片標題:左-原始圖
右-視覺化過濾器在圖片上的位置
記住,我們要做的是將過濾器的值與圖片的原始畫素值進行乘法運算。
圖片內容:視覺化的接受域 的畫素值 * 過濾器的畫素值
相乘和相加 = (50*30)+(50*30)+(50*30)+(20*30) +(50*30)=6600. (一個很大的數字!)
一般來說,如果輸入圖片的形狀與過濾器所表現的曲線相類似,那麼我們的乘積的和會是一個很大的數值。現在,我們嘗試移動過濾器,看看會發生什麼。
圖片內容:過濾器在圖片上的位置 接受域的畫素值*過濾器的畫素值
相乘和加和 = 0
這個值相比上一個要低很多!這是因為圖片中沒有任何部分與曲線檢測過濾器對應。記住,這個卷積層的輸出是一個啟用對映。在這個只有一個過濾器(並且這個過濾器是曲線檢測器)的卷積的案例中,啟用對映會顯示出圖片中那些與過濾器的曲線相類似的區域。該示例中,28 x 28 x 1的啟用對映的左上角的值將為6600。這個很高的值意味著輸入中包含著某種型別的曲線啟用了過濾器。啟用對映的右上角的值是0,因為所輸入的值並沒有啟用過濾器。(或者更簡單的說,圖片的右上角沒有這樣一個曲線)。這僅僅是一個過濾器,一個可以檢測出向右外側的曲線的過濾器。我們可以擁有更多的過濾器,如向左的曲線或者直線。過濾器越多,啟用對映的深度越深,我們從輸入中取得的資訊也就越多。
免責宣告:在本節中的所描述的簡化版的過濾器,是為了說明一個卷積中所涉及到的數學問題。在下圖中,你可以看到一個已經訓練好的神經網路中,第一個卷積層中過濾器視覺化的一些示例。但它們主要的想法還是一致的。第一個卷積層中的過濾器對於輸入的圖片進行卷積,當過濾器所代表的某個具體特徵在輸入中被發現時,過濾器就會被“啟用”(或者得到很高的值)。
(提醒:上面的圖片來自於史丹佛大學Andrej Karpathy 和Justin Johnson任教的 CS 231N 課程,如果想要更深入地瞭解CNN,這門課是你的不二選擇。)
更深入地瞭解神經網路
在傳統的卷積神經網路架構中,各個卷積層中穿插了其他的一些層。我強烈鼓勵大家去了解這些層的具體功能和效果,但簡單來說,這些層提供了非線性和保留維度的功能,從而提升神經網路的魯棒性,並能防止過度擬合。一個經典的CNN架構如下:
輸入-> 卷積->啟用-> 卷積->啟用->池化->啟用-> 卷積->啟用->池化->全連線
神經網路的最後一層是很重要的一個層,我們稍後會進行具體介紹。讓我們先回顧一下到目前為止我們所學的內容。第一個卷積層上的過濾器是用來發現特徵的,透過這些過濾器可以發現低層次的特徵,例如邊和曲線。然而,為了預測圖片型別,我們需要讓神經網路識別出高層次的特徵,例如手、爪子或耳朵。讓我們思考一下,神經網路中第一個卷積層的輸出是什麼?應該是一個28 x 28 x 3的體量。(假設我們使用的是3個5 x 5 x 3的過濾器)。
當我們進入另一個卷積層的時候,第一個卷積層的輸出就成為了第二個卷積層的輸入。接下來的步驟很難被視覺化。在第一層中,輸入是原始的圖片。然而,當我們進入第二個卷積層的時候,第一層的計算結果,啟用對映就成為了第二層的輸入,每個輸入都描述了某些低層次特徵在原始圖片中出現的位置。現在當你使用一組過濾器(讓它透過第二個卷積層)時,輸入中被啟用的部分就代表了高層次特徵。
這些特徵可能是半圓形(由一條曲線和一條直線組成)或者方形(由幾根直線組合而成)。當你使用更深層的神經網路和更多的卷積層時,你將得到更復雜特徵的啟用對映。訓練完神經網路後,你會得到一些過濾器,當圖片中是手寫字母時它們會被啟用,或者當識別到粉色時被啟用等等。如果你想進一步瞭解卷積網路中過濾器的視覺化,你可以參考Matt Zeiler 和 Rob Fergus一篇很優秀的研究報告(http://www.matthewzeiler.com/pubs/arxive2013/arxive2013.pdf)。你也可以在YouTube上看到Jason Yosinski做的一個很精彩的視覺化展現影片(https://www.youtube.com/watch?v=AgkfIQ4IGaM)。還有一個有意思的事情是,當你使用更深層的神經網路,過濾器所覆蓋的接受域會逐漸變大,這意味著過濾器考慮了原始輸入中更大範圍的資訊(換句話說,這些過濾器對於更大範圍的畫素空間反應更敏感)。
全連線網路層
既然我們已經可以檢測到這些高層級的特徵,接下來我們就需要一個全連線網路層作為神經網路的結束層。該層將之前層(卷積層、啟用層或者池化層)的處理結果作為輸入,並輸出一個N維的向量,N是程式所選擇的類別的數量。例如你想做一個數字識別程式,一共有10個數字,那麼N就是10。這個N維向量中每一個數字表示了目標物件屬於該類的機率值。例如,一個數字識別程式的結果向量是[0 .1 .1 .75 0 0 0 0 0 .05],它的意思就是這個圖片有10%的可能性是1, 10%的可能性是2, 75%的可能性是3,以及5%的可能性是9(注:你也可以使用其他方式表示輸出,在這裡我使用了Softmax迴歸模型的方法)。全連線網路層的功能是透過分析前一層的輸出(代表高層次特徵的啟用對映)決定哪些特徵值和某一個特定的類別相關性最高。
例如,如果程式預測某張影像是一條狗,它就會在代表一個爪子或四條腿等高階特徵的啟用對映中有較高的值。類似的,如果程式預測某張影像是一隻鳥,它就會在代表翅膀和喙等高階特徵的啟用對映中有很高的值。本質上講,一個全連線層關注與特定類相關性最強、並且有特定權重的高層特徵,以便能在計算權重與前面一層乘積後得到不同類的正確機率。
模型訓練
現在我要說的是我之前故意沒有提到一個話題,它也可能是CNN最重要的部分。閱讀中你可能已經產生了許多疑問:過濾器如何在第一個轉換層知道它要尋找的邊緣和曲線?完全連線層如何知道要檢視什麼啟用對映?每個層中的過濾器的值要怎麼確定?這些都是透過一個叫“反向傳播”的訓練過程實現的。透過這一訓練,計算機可以正確調整其過濾值(或權重)。
在討論反向傳播之前,讓我們先看一下使神經網路工作的條件。在我們出生的那一刻,我們的意識是一張白紙。我們不知道貓、狗、鳥是什麼。類似地,在卷積神經網路被訓練之前,權重或過濾值都是隨機的。過濾器不知道如何查詢邊緣和曲線,在更高的層的過濾器不知道尋找爪子和喙。隨著年齡的增長,我們的父母和老師給我們展示了不同的圖片和影像,並告訴我們相應的標籤。這個讓影像和標籤一一對應的想法就是CNN訓練的過程。
讓我們回到反向傳播。假設我們有一個訓練集,它有數千張狗、貓和鳥的影像,並且每一個影像都有一個正確的標籤。
反向傳播可以分為4個不同的部分:前向傳遞、損失函式、後向傳遞和權值更新。在向前傳遞時,你接受一個訓練影像(它是一個32×32×3的陣列),並透過整個網路傳遞它。在我們的第一個訓練示例中,由於所有的權重或篩選值都是隨機初始化的,輸出可能類似於[.1 .1 .1 .1 .1 .1 .1 .1 .1 .1],基本上是一個不優先考慮任何數字的輸出。以其當前的權重,這一神經網路是無法查詢那些低階的特徵的,因此也無法對影像作出合理的分類,這就是反向傳播損失函式的一部分。記住,我們現在使用的是訓練資料,此資料既有影像又有標籤。比方說,輸入的第一個訓練影像是3,影像的真實標籤就是[ 0 0 0 1 0 0 0 0 0 0 ]。損失函式可以有許多不同的定義方式,一個常見的定義是MSE(均方誤差),即½乘(實際值-預測值)的平方。
假設變數L等於那個值。可以想象,第一張訓練影像的損失將非常高。現在,讓我們直觀地思考這個問題。我們想使得預測標籤(ConvNet輸出)與訓練集的實際標籤儘可能吻合(這意味著我們的網路預測是正確的)。為了達到這一目標,我們要儘量減少我們的損失。讓我們把這一問題看作是微積分中的一個最佳化問題——我們想找出哪些權重最直接地導致網路的損失(或錯誤)。
現在,我們要做的是在網路中進行反向傳遞,它決定了哪些權重造成了最大的損失,並找出調整它們的方法,以減少損失。一旦我們計算出這個導數(dL/dW,W是權重),我們就可以進入最後一步,即權重更新。在這一步,我們對過濾器的權重進行更新,更新的方向即是我們剛才計算出的導數/梯度的反方向。
學習率(Learning Rate)是由程式設計師選擇的引數。高學習率意味著在權重更新中採取更大的步驟,因此,該模型可能只需要較少的時間來收斂到最優的權重集上。然而,學習率過高可能導致跳躍過大而不夠精確,無法收斂至最佳點。
正向傳遞、損失函式、後向傳遞和引數更新過程是一個訓練迭代過程。程式將重複這一過程,為每一組訓練影像(通常稱為批處理)進行固定次數的迭代。在我們完成最後一個訓練示例中的引數更新後,如果一切正常,網路就已經得到了足夠的訓練,即網路的權重得到了正確的調整。
測試
最後,為了檢驗我們的卷積神經網路是否有效,我們需要一套不同的影像和標籤(不能在訓練和測試之間重複使用!)。我們用訓練過的卷積神經網路對圖片標籤作出預測,再比較輸出和這些圖片的真實標籤,以檢驗我們的網路是否能正常工作。
企業如何利用卷積神經網路
資料,資料,資料!相比其他競爭對手,那些擁有海量資料的公司有著先天的優勢。你給網路提供的訓練資料越多,你可以做的訓練迭代越多,你能做的權重更新就越多,而當你投入到生產中時,對網路的調整就越好。Facebook和Instagram可以使用數十億使用者當前的所有照片,Pinterest可以使用其網站上的500億個引腳的資訊,谷歌可以使用搜尋資料,亞馬遜可以使用每天產品銷售產生的數以百萬計的資料。而現在,你已經知道了使用這些資料背後的秘密了。