近段時間,因爲工做須要,一直在看深度學習的各類框架,主要是Caffe和Tensorflow。而且在可預見的將來,還會看更多不一樣的深度學習框架。最開始我是以軟件工程師的角度去閱讀這些框架的,說實話,Caffe的代碼框架邏輯清晰相對好理解一點,而TensorFlow就比較麻煩了,裏面內容太多,函數調用鏈很是長,且使用了大量的C++11語法,這對於C++功底很差的我來講無疑是重大打擊...所以,我必須跳出軟件工程師的思惟,以算法工程師的視角來審視這些框架。考慮到它們都是爲深度學習服務的,所以我轉而去思考深度學習的本質,希冀可以舉一反三。算法
鑑於深度學習與神經網絡的關係相似於漂移與汽車的關係。深度學習能夠理解成用(深度)神經網絡來進行機器學習,漂移能夠理解成用汽車來作一些風騷的走位操做。所以,個人思考重點又聚焦到神經網絡身上。網上對神經網絡的解釋很是多,但通常都是直接扔給你一大堆陌生的名稱以及一堆看起來就很煩的公式,配合上他們說教的語氣,給人的感受就是:你看,神經網絡就這麼簡單,你如今一臉懵逼以爲複雜是由於你沒我厲害,跟着我學幾年也許你就會了。數組
不能否認,這些專有名詞和公式很是重要,可是咱們也必須知道全部的名詞和公式都是數學家爲了方便運算/記錄,而對某些概念或者規則進行的抽象處理,所以咱們應該先理解這些名詞或公式背後的概念或規則,而後再來反推這些公式,這纔是最合理的學習方式。那麼這麼多名詞與公式,我應該從哪入手呢?即在整個神經網絡中哪一個概念是最重要、最核心的呢?冥思良久,Tensorflow這個單詞給了我答案。它能夠拆分爲Tensor + flow,顯然在Google看來基於神經網絡的深度學習框架本質上就是:像車間流水線同樣對各類Tensor進行處理。好,那麼咱們就以Tensor爲入口探究深度學習的本質。網絡
Tensor譯做「張量」(多是爲了展現它同向量、矩陣之間的聯繫吧),但說實話,我徹底沒法從它的中文名字中理解到它的含義,所以本文就直接使用它的英文名了。Tensor是衆多深度學習框架中的一個核心組件(可能其餘框架中不叫Tensor,好比caffe中叫作Blob,但其內在含義都同樣,因此咱們徹底能夠將caffe叫作Blobflow),後續幾乎全部的操做和運算都是基於Tensor進行的。本章將會從Tensor的起源開始,逐步添加各個領域的一丁點知識來闡述我對Tensor在深度學習領域的理解。我能夠保證,絕對不會有一個公式。架構
在瞭解Tensor以前,咱們須要簡要回顧一下在高中/大學時學過的另外3個重要數學概念:scalar(標量), vector(向量), matrix(矩陣)。框架
那麼Tensor跟它們三個有什麼關聯或者不一樣呢?有人說Tensor就是向量和矩陣的擴展,通俗一點,能夠將標量視做零維Tensor,向量視做一維Tensor,矩陣視做二維Tensor...看起來是那麼回事,但其實錯得離譜!由於它將Tensor最本質的特性給丟掉了!機器學習
追本溯源,Tensor實際上是物理學家提出的一個概念,主要用於描述「物理定律不隨着參考系變化的這一性質」——A tensor is something that transforms like a tensor。然後再由嚴謹的數學家進一步加以抽象和發展,懂了麼?呃....等等,怎麼感受越解釋越抽象了?下面咱們開始說人話,請觀察下面一張圖:ide
你看到的是老婦仍是少女?不一樣的人以不一樣的方式去觀察這張圖片,會給出不一樣的描述。就我而言,看到的是:一位背側咱們的少女,少女的脖子上有一串項鍊,一頭飄逸的長髮半遮她的耳朵。而其餘人可能看到的是:一位老婦的側面,少女的耳朵變成了老婦的眼睛,少女的項鍊變成了老婦的大嘴~函數
那麼如今我問你,不管咱們得出的結論是老婦仍是少女,它是否是描述的同一幅圖片?答案是確定的,只是因爲咱們觀察的方式不一樣,而得出了不一樣的結論而已,且這些不一樣的結論並無對錯之分,它只表示按照咱們的方式看來就是得出這樣的結論。回看前文說起的物理學家對Tensor的描述,咱們能明顯找到二者的共通性:這幅不變的圖片就是「不變的物理定律」,而不一樣的人採起了不一樣的觀察方式其實就是「選用不一樣的參考系」,他們得出的結論本質上沒有對錯高下之分。那麼我如今說:正以下圖所示,==Tensor就是這幅不變的圖片在不一樣觀察方式下得出的描述==,你能理解了麼?學習
下面再來看看數學家是怎麼描述Tensor的。在線性代數中一般有這種說法:矩陣的意義是線性變換,類似矩陣是同一個線性變換在不一樣基下的表示。劃重點,這裏的「同一個線性變換在不一樣基下的表示」不就說的是Tensor麼!顯然,在數學家眼中,Tensor已經被抽象成了線性變換,若是咱們將線性變換看作一個函數的話,正以下圖所示:ui
至此,Tensor在數學上的含義咱們就再也不展開了,由於這已經足夠咱們理解深度學習中Tensor的意義。
這裏咱們只須要簡單理解生物學裏面的視覺感知系統就好。先看幾組動物與人類在視覺感知上的差別對比圖:
1 蒼蠅與人類的視覺感知差別:
左邊是人的視覺感知,右邊是蒼蠅的視覺感知
2 蛇與人類的視覺感知差別:
更多的視覺差別對比見這裏。
經過上面的對比圖能夠知道,即使是相同的場景,通過不一樣的視覺系統,也會獲得不一樣的感知。用生物學上的解釋就是:生物所看到的鏡像並不是世界的原貌,而是長期進化出來的適合本身生存環境的一種感知方式。也就是說:
物體光線的反射 -> 某生物的視覺感知系統進行各類處理 -> 產生該生物腦中對該物體的感知(概念)——正如上圖所示。這跟Tensor在物理、數學上的定義是否是很是類似呢?因此說,目前在深度學習領域用得最廣最成熟的圖像識別技術,其本質上並非識別這個圖像在客觀上是什麼,而是不停地訓練該識別系統,以到達模擬人類視覺感知的程度。所以,當你發現本身的圖像識別系統老是識別錯誤的時候,也不用驚慌,由於你可能恰好訓練出了M8星雲奧特兄弟們的視覺感知,而不是人類的視覺感知,若是踩了狗屎運大家的業務方又恰好是奧特兄弟的話,那麼也算是圓滿完成項目了^_^。
一樣的,咱們能夠將之推廣到模擬人類聽覺感知系統的語音識別等等。正是基於此,早期的神經網絡也稱之爲「(多層)感知機」。
數字圖像通常分爲「位圖」和「矢量圖」。位圖是由「點陣」組成的,計算機在存儲或處理位圖的時候是處理這個「點陣」,每一個點描述的是該位圖中一個像素點的灰度;而矢量圖是由線條和填充於線條所圍成的區域之中的灰度組成的,計算機記錄如何繪製這些圖形,而不記錄「點陣」。這裏咱們只關心位圖。以最簡單的灰度圖(就是你們所謂的黑白圖片)爲例,好比一張400 x 400像素的灰度圖,其本質上就是一個400x400的矩陣,矩陣中每一個元素就是一個像素點。每一個元素取值0~255之間的整數,表明256種灰度等級。灰度值越大,像素的顏色越‘白/淺’;灰度值越小,像素的顏色越’黑/深‘。好比下圖字符8的圖像以及其對應的灰度值矩陣表示以下:
那麼彩色圖片在計算機中是怎麼表示的呢?以經常使用的RGB圖片爲例。RGB是一種數字圖像顏色模型,其中R表明Red紅色,G帶便Green綠色,B表明Blue藍色。咱們能夠簡單地將之理解爲:RGB就是以紅綠藍三原色的組合來展現一張彩色圖像。以下面這張經典的圖片所示(爲描述方便,假設爲400x400像素的RGB圖片):
其實它是由3個分別在紅、綠、藍顏色上的灰度圖組合渲染而成:
如你所見,每一種原色(也叫份量)單獨看都是一個400x400的灰度圖片,對應一個400x400的矩陣,所以這張RGB圖本質上就是一個400x400x3的三維數組。好了,關於數字圖像的一點點知識咱們就淺嘗輒止地介紹到這裏了,更詳細的信息能夠參考這裏。細心的讀者可能發現本節一直使用矩陣而非Tensor,那是由於在數字圖像領域人們會更直觀地將每張圖片理解成n維數組,而非Tensor。
下面我將直接告訴你,其實這些n維數組正確的稱呼就應該是「n維Tensor」! 回顧一下Tensor的概念,裏面有個很是關鍵的信息——「觀察方式」或者「參考系」或者某種規則。試想若是我直接將字符8的灰度值矩陣圖扔給你,你能脫口而出它是字符8麼?顯然是不能的,咱們只有將它交給計算機按照約定的規則渲染成字符8的位圖以後,你才能知道這個灰度值矩陣真正的含義。所以在數字圖像領域,其「參考系」或者「觀察方式」是隱式地定義在灰度值Tensor內部的,咱們只有使用事先約定好的規則才能正確地表示這些Tensor的圖像含義。所以,當之後使用深度學習處理圖像數據的時候,請叫它們Tensor而非數組或者矩陣。
經過前面的介紹,我相信你確定對Tensor有了一個比較直觀的理解。本質上Tensor就是對某個事物按照不一樣觀測方式得出的描述結論。==不過每次都這麼描述Tensor老是比較麻煩,所以人們爲了方便,就將得出的「描述結論」稱之爲Tensor,而再也不顯式說起該「描述結論」對應的「觀測方式」了,可是咱們必須在心裏時刻謹記Tensor真正的含義==。好比將「少女」, 「老婦」稱之爲Tensor;又例如在數字圖像領域,咱們約定使用一個3維的Tensor來表示一張RGB圖片。下面咱們將探討爲何Tensor是各類以神經網絡爲基礎的深度學習框架中最核心的組件。
咱們首先來看一下經典的用於識別0~9手寫字符的3層神經網絡長什麼樣:
是否是很複雜?那我把它簡化一下,好比只識別1個字符的3層神經網絡:
還有點複雜?那咱們再進一步簡化,好比輸入、輸出和中間層都只有一個結點的神經網絡:
如今再回顧一下咱們在第1章中反覆畫出的Tensor圖,它們是否是很是像呢?這裏咱們能夠列舉出三點共性:
每個圓形結點都表明對某個Tensor的一種處理操做,也能夠稱之爲感知;
圓形結點與圓形結點之間只傳遞Tensor;
都是有向無環圖,就跟工廠的流水線同樣,有明確的輸入和輸出,且Tensor的流動路徑固定。
我猜想這就是爲何叫Tensorflow而不叫TensorCircle或者其餘名字的緣由吧^_^~
基於上述分析,咱們能夠得出結論:神經網絡其實就是像流水線同樣對輸入Tensor依次進行一系列地處理,最終得出咱們想要的那個Tensor(結論)。
以大名鼎鼎的2012年Imagenet比賽冠軍的深度學習模型Alexnet爲例
其網絡結構圖以下:
看起來很是複雜,甚至已經由二維平面架構衍生到了三維立體架構,但它仍然知足咱們在2.1章節總結出的三點共性。所以它本質上仍是:對輸入Tensor依次進行一系列有向無環圖的處理,最終得出咱們想要的Tensor!
從前文的分析咱們得出了一個結論:深度學習就是對輸入Tensor依次進行一系列有向無環圖的處理,直至最終得出咱們想要的Tensor。你們可能會以爲這個結論不嚴謹,由於它看起來只描述了深度學習一半的性質——即推理(Inference)部分的性質。所謂的推理就是咱們使用已經學習/訓練好的能夠完成某個功能/任務的模型,對輸入Tensor按照既定順序邏輯進行處理,直至獲得該模型的輸出Tensor。而深度學習另外一個重要的學習/訓練性質並無在這個結論中獲得體現。事實是這樣的麼?其實在訓練階段也是一樣的思路,只不過Tensor發生了改變以及Tensor流動的方向相反了而已:使用反向傳播算法根據訓練結果的偏差Loss_Tensor來進行一系列處理,直至訓練出知足咱們要求的Weight_Tensor以及Bias_Tensor等等。以下圖所示:
至此,咱們已經發掘出深度學習的三個核心要素:
而目前全部的深度學習框架恰好都是以這三個核心要素爲出發點進行的架構設計!好比在Caffe中,使用了一個叫作Blob的類來描述Tensor並以數組的形式進行存儲,使用了一個Net類來描述Tensor處理序列的有向無環圖,使用了各類Layer類來描述對Tensor進行的各類處理,既包括用於推理的正向forward也包括用於訓練的反向backward,至於其餘的各類類都只是做爲後勤工做者來輔助它們而已;一樣的在Tensorflow中,使用Tensor類來描述Tensor,使用Graph類來描述Tensor處理序列的有向無環圖,使用各類Operation類來描述對Tensor進行的各類處理,而其餘的類也都是輔助類,只不過Tensorflow爲了方便算法工程師進行模型訓練而開發了很是很是多的輔助類而已。有了這個認知,之後再去閱讀其餘深度學習框架的源碼,就容易不少了,甚至咱們也能夠本身嘗試編寫一個深度學習框架。
注意:RNN循環神經網絡其也是一個有向無環圖,只是由於它引入了時間維度,爲了描述方便纔在其網絡圖中畫出了環而已,爲了不混淆,你也能夠將RNN稱做「遞歸神經網絡」。
古人云,大道至簡。深度學習的核心原理是如此之簡單,也是讓我一時難以置信。不過簡單的東西其優缺點也是很是明顯的:
優勢:理論基石穩固,不容易被推翻,君不見如今各類深度學習網絡架構層出不窮,但都逃不出咱們總結的三個核心要素麼?
缺點:簡單的理論要想用於解決複雜的問題,每每須要付出不少額外的代價,也許這就是深度學習不得不依賴於大量有效數據的緣由吧。
最後,要想真正看懂在深度學習框架中各類眼花繚亂operation操做,咱們還必須去深刻研究各類算法,好比反向傳播算法、卷積的原理等等,這些內容後續再慢慢補充吧。
Tensor(張量)的介紹
視覺感知的介紹
RGB圖像的介紹
RNN介紹
Neural Networks And Deep Learning
AlexNet的介紹
Caffe框架
Tensorflow框架