天天看點

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

自 2015 年 11 月首次釋出以來,tensorflow 憑借谷歌的強力支援,快速的更新和疊代,齊全的文檔和教程,以及上手快且簡單易用等諸多的優點,已經在圖像識别、語音識别、自然語言處理、資料挖掘和預測等 ai 場景中得到了十分廣泛的應用。

在所有這些 ai 應用場景中,或許是源于視覺對人類的直覺性和重要性,圖像識别成為其中發展速度最快的一個。目前,該技術已經逐漸趨于成熟,并在人臉和情緒識别、安防、醫療篩查和汽車壁障等諸多領域都取得了重大成功。

在這種情況下,對于絕大多數的 ai 開發者而言,利用 tensorflow 自己親手搭建一個圖像識别子產品,就成了一項最順理成章的挑戰。

為了幫助有志于此的開發者實作目标,也為了向那些親手搭建過圖像識别子產品的技術達人提供一個與行業大牛交流、學習的機會,本次公開課雷鋒網 ai 研習社有幸邀請到才雲科技(caicloud.io)聯合創始人、首席大資料科學家鄭澤宇,他将深入到代碼層為我們詳細講解究竟怎麼用 tensorflow 自己親手搭建一套圖像識别子產品。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

鄭澤宇,暢銷書《tensorflow:實戰 google 深度學習架構》作者,才雲科技(caicloud.io)聯合創始人、首席大資料科學家。才雲科技(caicloud.io)是一家雲計算、人工智能創業公司。最近推出全球首個商用 tensorflow as a service (taas) 深度學習平台和行業大資料解決方案,用資料助力企業成長。

鄭澤宇曾在 google 擔任進階工程師,作為主要技術人員參與并上司了多個大資料項目。提出并主導的産品聚類項目用于銜接谷歌購物和谷歌知識圖譜(knowledge graph)資料,使得知識卡片形式的廣告逐漸取代傳統的産品清單廣告,開啟了谷歌購物廣告在搜尋頁面投遞的新紀元。

鄭澤宇擁有 cmu 計算機碩士學位,在機器學習、人工智能領域有多年研究經驗, 并在 sigir、sigkdd、acl、icdm、icwsm 等頂級國際會議上發表多篇學術論文。

本次公開課的主要内容包括:

1. 深度學習簡介 2. 神經網絡工作原理 3. 用 tensorflow 實作圖像識别 4. 疑難問題解答及讨論

以下為公開課完整視訊:共 55 分鐘。

以下為公開課内容的文字及 ppt 整理。

大家好,今天我想跟大家分享一些深度學習算法在圖像識别上的應用。

主要内容大概可以分為如下三個部分:

● 深度學習介紹; ● 神經網絡工作原理; ● 用 tensorflow 實作圖像識别。
從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

深度學習介紹

我們知道深度學習現在是已經是一個非常熱門的技術,那大家第一次聽到這個深度學習的時候呢?很有可能就是因為去年這個時候 alphago 戰勝李世石的這個事情。當時這個事情獲得了全社會的廣泛關注和熱烈讨論。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

但其實 alphago 并不是第一個戰勝人類的智能機器人,早在 20 年前就有過 ibm 深藍機器人戰勝人類國際象棋冠軍的記錄。那為什麼 alphago 可以引發這麼大的關注呢?

我認為原因有兩個方面:一是圍棋的複雜度遠超國際象棋;二是因為深度學習技術的發展,它推動了不僅是一個 alphago 這樣的應用程式,它其實也推動了各個方面的人工智能的應用。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

例如谷歌的無人車項目,就是一個距離我們更近的例子。大家都知道,現在無論在國内還是國外,堵車和停車的問題其實都是很嚴重的。但是如果有了無人車這樣一個工具,就能大大提升車主的使用者體驗。

正是因為深度學習技術在 alphago 和無人車等項目背後的巨大推動力,才使得這些項目能夠發展到目前這樣一個比較高的水準。

但其實,深度學習技術并不是一個新技術,它的起源可以追溯到幾十年前,隻是這兩年才得到了一個比較快速的發展。如圖中所示的搜尋熱度變化圖也能看出,從 2012 年到 2016 年,深度學習這個詞的受關注程度是處于一個指數級增長的狀态。那為什麼會在 2012 年這個時間點出現這樣的一個增長呢?其實是因為 imagenet 這樣一個圖像識别的比賽。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

imagenet 是由李飛飛教授發起的一個著名的圖像識别資料集,裡面包括了各種各樣的圖檔,然後參賽者需要将物體從圖檔中标記出來,做一個分類。這個比賽每年都會舉辦,而且每次的比賽細節都會有所不同。然後在 2012 年的時候,由于深度學習的作用,比賽結果産生了一個巨大突破。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

從下圖可以看出,在 2012 年之前,采用了傳統分類算法的時候,錯誤率大概是 26% 左右。而且我們可以看到這個錯誤率的變化趨勢非常緩慢,也就是說要減低一點錯誤率,就必須付出巨大的努力。但是在引入深度學習算法之後,從 2011 到 2012 年,使得錯誤率從 26% 一下子降低到了 16%,并且從 2012 年開始的這三四年中,錯誤率還在以每年 4% 左右的一個速度在降低。到 2015 年,機器的識别率已經接近了人類的水準,即 5.1% 的錯誤率。2016 年,機器最新的識别正确率已經達到了 97% ,錯誤率達到了 3% 左右,已經比人類好得多。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

如下圖是才雲科技內建 google 訓練好的一個模型,它可以通過分析使用者上傳的圖檔,例如一頭牛,然後分析出這頭牛是某個品種的機率是多少。還有現在大家在 google 或者百度上傳一張圖檔,然後搜尋引擎就能比較精确地告訴你這個圖檔裡的主體是什麼動物,或者什麼植物,甚至還能提供一段簡單的文字描述等等。其實這些都是基于深度學習的算法來實作的。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

除了圖像識别之外,其實深度學習的早期應用是數字識别。例如圖中所示的這個就是 1998 年的時候 yann lecun 教授做的一個手寫體數字識别的項目(如下圖所示),用的就是深度學習技術。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

此外還有 google 在地圖上的應用,能夠通過圖像識别自動定位門牌号和地理位置等資訊。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

其實神經網絡,也就是深度學習技術用在圖像識别的應用還有很多,包括人臉識别、安防領域、火警、群衆事件,還有現在的美顔等等。并且,受到神經網絡思想的啟發,目前包括語音識别、機器翻譯、自然語言處理和大資料分析、預測等行業都得到一個比較大的發展。

神經網絡原理

下面簡單介紹一下神經網絡的情況。

這裡我不會去推導前向傳播或者反向傳播的具體過程。前向傳播的過程比較簡單,這裡會做一個大緻的介紹。而反向傳播對數學的要求比較高,并且通過 tensorflow 可以非常容易地去實作,是以我隻會簡單介紹一下基本原理,大家自己有興趣的話可以自己去深挖。這個部分我主要還是做一些流程上的介紹,讓大家知道一個完整的機器學習或者說圖像識别問題,我該怎樣一步一步地去解決它,包括我需要做哪些事,什麼事情可以通過什麼工具來幫助我實作。

首先我們來介紹一下什麼是深度學習。大家可能經常會聽到深度學習和神經網絡這些詞,但它們之間究竟是一個什麼關系呢?其實,深度學習在維基百科上的定義是:多層的非線性變換的一個算法合集。那怎樣實作這個多層非線性變換呢?最好最友善的一種方法就是神經網絡。是以說基本上目前來講的深度學習,就等于是深層神經網絡的一個代名詞。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

神經網絡,大家從這個詞就能看出它多多少少跟人腦的神經網絡有些關聯。如圖所示,左上角就是一個神經元的模型,他包括很多不同的輸入,以及一個軸殼來處理這些輸入,最終得到一個輸出。這個對應到人工神經網絡也是一樣的,它會有多個輸入,然後經過一些變換得到輸出。但人腦的變換函數具體是怎樣的,現在還弄不清楚,我們隻能通過這樣一組權重和,加上一個激活函數來模拟人腦。

大家都知道,人腦是通過這種神經網絡的網絡狀結構處理資訊的,是以在人工神經網絡結構中也是通過這樣的一種多層結構來實作神經元的連接配接。如上圖的右下角所示,每一個圓圈都代表一個神經元,多個輸入,一個輸出,上一層的輸出作為下一層的輸入。

下面我簡單介紹一下怎麼用這個網絡結構來處理問題。比如數字識别問題,如圖所示的數字圖像在計算機裡就是一個像素矩陣,然後每個矩陣元素裡面都是各種各樣的一個數字,我們把這些數字作為這個神經網絡的輸入層提供進來,然後通過不同結構的神經網絡處理,從輸入層到隐藏層再到輸出層,就可以得到處理結果。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

比如圖中的這個手寫數字問題,其實就是要識别這個數字到底和 0 到 9 中的哪個數字更像一點。我們可以安排輸出層有 10 個結點,分别代表 0 到 9 的 10 個數字。那麼如果這個圖像是 1 的話,我們就希望代表 1 的這個結點輸出的結果是 1 ,其他的結點是 0 。這樣的話假設我們輸入一張圖像,然後發現代表數字 7 的結點輸出為 1,其他結點為 0 ,那麼我們就等于識别出了這個圖像的内容是 7,也就完成了一個數字識别的任務。

這隻是一個最簡單的例子,還有更多更複雜的神經網絡這裡我們就不做具體介紹了,感興趣的朋友可以關注才雲科技開源的一個代碼庫,裡面有各種豐富的樣例代碼。(雷鋒網注:開源位址見下文連結)

下面簡單介紹一下深度學習的兩個大的分類:監督學習和非監督學習。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

我通常會把機器學習和人類學習來做一個對比,其實有很多地方都是比較類似的。例如我們小時候去上課,然後考試。其實機器學習也是一個類似的過程,它通過海量的資料,然後學習(總結)出一些對應的規律,并将規律應用在一個測試環境上,就能得到一個諸如正确率這樣的評測名額,最終通過評測名額來評測一個機器學習算法的好壞。

那麼在監督學習的場景中,通過海量的标記過的資料,就相當于人類在學習中通過大量的做題,然後每做一個題都知道對錯,沒有錯的話就加強這個過程,有錯的話就反向改進,這就是監督學習。

而非監督式就不需要人為的标簽資料,它是監督式和強化學習等政策之外的一個選擇。典型的非監督學習有聚類等,它是直接從資料中尋找相似性,即規律。

現在其實機器學習除了監督式和非監督式之外,還有增強學習。它是和監督式及非監督式都有些不同的一種方式。然後,但其實在工業界用得最多的,其實還是監督式學習的方式,非監督式和增強學習現在在工業界的使用還是相對比較少。那其實我們今天也會主要以監督式的這種學習方式作為一個樣例,來告訴大家怎樣去完成一個監督式的學習方法來完成圖像識别工作。

在具體介紹整個模型之前,這裡我先跟大家詳細介紹一下神經網絡的工作原理。

剛剛講到,我們要去做一個圖像分類子產品,就相當于是把這個圖像的原始的像素矩陣傳入輸入層,然後經過一層一層的推導,得到輸出層。那其實神經網絡裡面一個最關鍵的部分,就是說我怎樣通過一層一層的網絡結構來得到從輸入層到輸出層的結果。最簡單的來講,我們先要知道一個單一的神經元的工作方式。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

如圖所示,我們其實可以将每個神經元視為這樣的一個多項式組合,w表示權重,b表示偏移量。那麼訓練時一個最重要的工作就是找到最合适的權重,使得我們的實際輸出與預想輸出一緻。那麼輸入的一個權重平均,加一個偏移,最後再通過一個激活函數,最後就能得到輸出。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

這裡我們以一個判斷零件是否合格的例子來講解,注意這裡省略了偏移量和激活函數。比如說我這裡的每一個零件它都會有長度、品質等參數,就相當于收集了很多關于這個零件的資料,其中有一些我們知道是已經合格了的,也就相當于有了一個訓練資料。将這些訓練資料輸入模型,通過結果對比不斷調節隐藏層的權重參數,最終達到一定的正确率之後,也就是完成了模型訓練。接着我們可以測量任意一個零件的參數,把測量資料輸入神經網絡,就能判斷這個零件是否合格。

這樣的一個過程其實就是正向傳播的一個過程。反向傳播相當于是我知道一個零件的長度和品質,也知道它是否合格的時候,再去根據這個目标做一個反向的回饋。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

這裡我列出了一些簡單的激活函數,注意這裡所有的激活函數都是非線性的函數。如果一個模型沒有激活函數的話,就相當于是所有線性過程的疊加,不論模型有多少層,疊加出來還是一個線性過程,也就是模型沒有涉及非線性的因素,也就不會有實際的應用。而激活函數就是一個提供非線性過程的因子,有了激活函數我們才能完成一個非線性變化的過程。

更詳細的内容大家可以參考《tensorflow:實戰google深度學習架構》這本書。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

這裡我們介紹兩種常用的激活函數:softmax 和 sigmoid。在多分類的問題中,經過層層的推導,其實每個節點的輸出都是不一定的。那麼如果我們想得到一個機率分布,就需要用到 softmax 這樣一個層。它相當于對每個輸出節點的大小作為置信度做一個歸一化的操作,然後使得每一個最終輸出節點的值都在 0 到 1 之間,這樣就等于輸出了一個機率分布。我們可以大概了解為不同的輸出類别的一個機率分布。在多分類問題中,一般都會用 softmax 作為最後的處理層,得到一個機率分布情況。類似的,在二分類中我們通常使用 sigmoid 函數。

這樣,從輸入層到隐藏層到輸出層再到激活函數,我們等于介紹了全連接配接神經網絡的一個基本結構。剛剛提到,監督學習就是我們得到一個結果之後,能夠判斷它的好壞。那麼怎麼判斷和評測呢,就需要損失函數。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

通過損失函數,我們可以計算出實際輸出和真實标簽的差别,然後進行優化,縮小這種差别。兩個經典的損失函數一個是交叉熵,另一個是 mse 最小平方差。他們詳細的用法,包括自定義函數怎麼樣去定義等内容,大家可以參考《tensorflow:實戰google深度學習架構》這本書。

定義完損失函數,我們再來講講優化。

首先,優化的是什麼?我們剛剛提到,神經網絡裡的每一個神經元都有參數,我們要優化就是這些參數。那怎樣來優化呢?就是通過我們定義的損失函數,即推導得出的結果要跟真實結果越接近越好。這相當于變成了一個最小化問題。最小化問題确實有比較成熟的數學解法。但對于神經網絡這麼複雜的一個結構,它其實并沒有特别好的數學公式能夠直接求解。

雖然說,優化神經網絡的算法有不少,但主體的思想其實都是基于梯度下降,或者随機梯度下降。那麼,梯度下降是什麼?用簡單的話來講,它就相當于是把不同參數的取值和損失函數的大小,看成空間中的一個曲面。最簡單的情況下,可看成二維空間上的一條曲線。任意一個參數的取值,就對應了損失函數的取值。這樣子的話,我們就可以通過計算它的梯度來修改參數,使得損失函數會往更小的這樣一個方向去發展。這就是優化神經網絡的最基本的思想。包括反向傳播算法,其實也就是怎麼更快地去計算出每一個參數的梯度,使得計算的時間複雜度減少。優化神經網絡的核心思想其實還是梯度下降。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

梯度下降是在所有的資料集上去算它的梯度。但神經網絡的資料量一般會比較大,一般很難把所有的資料全都用上。這樣的時候,我們一般會采用 minibatch。一次計算部分的梯度來減少計算量。本來我們就知道,梯度下降其實就已經無法達到全局最優值。那使用随機梯度下降呢,其實就更加難以保證達到最小值,有全部訓練資料集才能有最小值。但我們可以通過調整學習率,使它更加逼近極小值。

這些就是我想給大家講的,神經網絡的大緻工作原理。其實這個工作原理講得比較粗淺,也比較 high-level。但大部分人其實對主要的一些部分了解就 ok 了。

用 tensorflow 實作圖像識别

接下來,我會把這些原理對應到具體的代碼裡面,然後讓大家知道怎麼樣通過 tensorflow 來實作圖像識别。同時講解怎麼用 tensorflow 來實作大緻的機器學習分類算法。

雖然上面有很多的細節沒有覆寫,但其實 tensorflow 也把這樣的一些細節給屏蔽掉了。我的意思是,其實大家隻需要了解一些比較 high-level 的東西,就完全能夠通過 tensorflow 來實作神經網絡的訓練。

我們先談什麼是 tensorflow,為什麼要選擇 tensorflow。

tensorflow 是谷歌在 2015 年底開源的一個深度學習架構。雖然說是深度學習,官方來講,其實 google 希望把它做成一個計算工具。但這個計算工具的主要任務,就是用來實作深度學習算法。是以說,其他的功能我們暫時也就抛開不談。就深度學習的基本功能來講,tensorflow 已經得到廣泛的應用。google自不必提,現在所有 google 内部的深度學習系統全都是基于tensorflow。deepmind 賣了之後,推出的東西也都會基于tensorflow。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

google 之外,國内包括華為、京東、小米,其實都在用 tensorflow。國外像 twitter、uber、snapchat 也在用。使用它的公司其實非常多。現在學術界也好,工業界也好,都偏向使用它。為什麼 tensorflow 會這麼受歡迎?除了有大公司的背書,社群的貢獻度也是非常重要的一個參考名額。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社
從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

在 github,無論是從 star 的數量,fork 的數量,還是從 issues 和 pull request, tensorflow 都遙遙領先于其他同類深度學習開源架構。對于深度學習來講,它還是一門正在發展中的技術。對于工具來講,我們認為,它是否能夠跟上這門技術的發展,其實是非常重要的一個考核标準。就是說,因為技術的發展是非常快的,如果工具的發展落後于技術的發展,它就會有一個被淘汰的風險。是以說,當它的社群活躍度非常高的時候,這個風險度就會相應的降低。是以我們比較推薦使用 tensorflow。對于新手來講,我們也比較推薦。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

這裡給出了一個簡單的 tensorflow 的 hello world 的程式,實作了一個簡單的向量加法的操作。首先 import 了 tensorflow ,然後定義了 a、b 兩個向量,包括 name 屬性,接着把它們加起來。這裡 tensorflow 采用了這樣的一個惰性計算模型,輸出的并不是加法的結果,而是結果的一個引用。另外,要運作整個 result 運算,就必須定義一個 session ,session 會掌握所有 tensorflow 的運算資源,然後通過 session 運作相關操作。

這裡隻是簡單介紹了一個 tensorflow 的簡單用法,由于時間有限,也無法深入地去詳細介紹。我們關注的是如何用 tensorflow 實作一個神經網絡的全連接配接,也就是權重和,加上激活函數的模型。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

權重和可以通過矩陣乘法的方式實作。如上圖代碼所示,這裡通過 placeholder 的方法定義了一個 input ,其中類型是必須的,其他的諸如 shape 等參數則可以等使用的時候再指派。之後定義了權重 w 和偏移量 b,這裡是通過 variable 方法定義的,這樣等最後優化的時候,tensorflow 會針對這些 variable 展開優化。最後通過乘法和加法操作,也就是通過 output = tf.nn.relu(tf.matmul(x, w) + b) 這一行代碼就實作了神經網絡的基本結構。

這裡是通過基礎的 tensorflow api 實作的,如果通過 keras 等更高層的封裝來實作會更加簡單。這裡我們是從基礎的 api 入手來進行講解,如果大家對高層封裝感興趣,可以自己學習。需要指出的是,其實高層封裝和基礎 api 的主要差別是實作上的差別,他們整體上的過程是基本一樣的。

下面我們來看一下如何用 tensorflow 實作一個具體的圖像識别子產品,即從 mnist 資料集中識别手寫數字。(完整代碼見下文連結)

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

可以看到,tensorflow 通過 read_data_sets 方法對引用資料進行了一個非常好的封裝,後續可以通過非常簡單的方式讀取這些劃分好的資料集,例如通過 train、validation、test 等關鍵詞就可以讀取訓練和測試資料集等。

如下圖所示,然後是通過 next_batch 來擷取一小批的訓練資料。我們剛剛提到,在利用梯度下降算法時需要在所有的訓練資料上計算梯度,但是計算量太大了,是以這裡通過 next_batch 方法,相當于我們在所有的訓練資料集中篩選一部分,随機選取一部分訓練資料集,提供到神經網絡的輸入層,然後通過反向疊代方法去優化這個神經網絡。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

這裡 xx 設定等于 100,也就是我們得到了 xs 和 ys 兩個矩陣,xs 代表輸入數組,相當于把一個 28×28 的手寫圖像展開成一個長度為 748 的一維數組。ys 相當于我們的結果,也就是 0-9 這 10 種可能值。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

如上圖,完了之後是一個前向傳播的一個大緻過程的程式截圖。這個過程就相當于是定義一層一層的神經網絡結構,這裡 inference 函數中的 input_tensor 相當于輸入矩陣,後面的 reqularizer 就相當于一個正則化的東西。我們可以看到,當輸入來了之後,程式開始進行一層一層的推導,定義一層一層的權重和偏移量,算出每一層的結果,傳入下一層,進入下一層的計算。

其實通過這個前項傳播的定義我們可以看到,無論是全連接配接層還是卷積神經網絡,甚至是循環神經網絡,它的大緻流程都是一樣的,給定輸入,然後通過一層一層的傳遞就可以得到最後的輸出。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社
從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

如上圖,下面我們看一下主程式。其實主程式就是調用了 train 的過程,這個 train 的過程其實也是比較簡單的。第一部分是定義輸入,也就是怎樣來提供這個訓練資料的接口,也就是通過 placeholder 的方式導入,輸入這裡是 x ,輸出是 y_ 。然後通過調用 inference 函數來進行一個前向傳播的計算。然後定義了滑動平均和損失函數。

這裡的過程其實是就相當于是:我通過輸入一個訓練資料集,然後得到在目前資料集下的推導結果,然後再通過這個推導結果和正确答案對比,就知道跟正确答案的差别在哪。下一步可以看到我們定義了 loss ,它相當于評估目前模型好壞的一個名額。這裡其實就相當于是評價 cross_entropy 加上正則化,這裡正則化是為了避免過耦合的。

完了之後,下一行是通過 gradientdescentoptimizer 函數優化。tensorflow 提供了大概 5-7 中不同的優化函數可供選擇,它們針對不同的應用場景,各具特點,大家可以靈活選擇。這裡我認為,對于那些不搞學術研究的同學,其實沒有必要去從數學的角度推導每一個優化函數具體是怎麼優化的,從應用層的角度來看,大部分使用者隻需要提供學習率和目标函數,并且了解這些優化函數的優劣就可以了,這個相對來說還是比較友善。

在把所有的這些計算方式都定義好了之後,下面就是生成 tensorflow 的計算圖,以及生成 session。定義好 session 之後,下面訓練的過程就比較簡單了,其實就是寫了一個循環,每次選取一小部分訓練資料,然後去做訓練,隔一段時間再列印一下訓練結果,整個過程就完成了。

是以說整個用 tensorflow 來實作一個神經網絡的過程,相對還是比較簡單的。需要注意的是,這裡我介紹的隻是原生态的 tensorflow,如果大家要去使用 tflearn,或者 keras 這些進階封裝去實作 mnist 問題的話,可能會更加簡單,大概隻需要 2-3 行代碼就可以解決了。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

這裡我們基本上把通過原生态的 tensorflow 生成神經網絡的過程為大家介紹了一下。其實後面還有個 evaluate 評估的部分(代碼如上圖所示),因為時間關系我就不對着代碼詳細講了,感興趣的同學可以自己下去研究(源碼見下文連結)。

下面我再跟大家再介紹一下循環卷積神經網絡。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

剛剛大家看到的這個結構是一個全連結的神經網絡,在圖像處理的過程中,使用全連接配接神經網絡最大的一個問題就是它的參數太多了,這個問題可能會導緻模型最終訓練不好。

例如,經常發生的,當你的訓練資料不足的時候,參數又太多,你就可能訓練不出來。一個非常簡單的例子,大家可以想象 n 元的一個方程組,然後我們假設隻有 n 個資料,并且這些資料是完全可分的,也就是我們是可以完全求解。但完全求解可能會導緻過拟合,因為訓練資料在真實環境下都是有噪音的,也就是沒有辦法做到完全避免随機因素的影響。在這種情況下如果你過于貼合訓練資料,那麼就有可能沒有辦法去收斂到未知的資料。

是以這就是參數過多可能引發的問題,即過拟合和訓練不出來。那怎樣去解決這兩個問題呢?卷積神經網絡就是一個很好的方法。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

卷積神經網絡就相當于是采用一個核心,即一個規模較小的矩陣,去處理一個比較小的區域,然後去通過移動這個小矩陣,去處理不同的這個塊。這種方式一個直覺的一個意義就是:一般的圖像上相鄰區域的内容是相似的。然後通過這樣的一個潛在的東西,就可以去把一個淺層的表達變成一個更深層的表達。也就是相當于自動從圖像中去提取特征。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

例如上圖所示,第一層可能可以從圖像中提取一些線條和斑點,第二層提取一些更複雜的性狀。第三層和第四層,層數越多,提取的特征就會越複雜。然後通過最後提取出來的這樣一些特征,我們再去做一個全連接配接的分類,最後這個分類的效果也就會更好。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

然後這裡給出了一個簡單的 lenet5 的模型,我們可以看到他的大緻結構就是從輸入層,經過不斷地卷積池化,再經過 1 到 3 層不等的全連接配接層,最後得到輸出層。其實作在很多的卷積神經網絡基本上也都保留了這樣的一種結構。

除了這種模型之外,另一種比較特殊的模型是 google inception 模型,這裡因為時間關系我也不去做過多的介紹了。

然後我在這裡給出了一個簡單的用 tensorflow 的程式來實作卷積層。通過代碼其實大家也可以看到,在這個架構裡面,無論是全連接配接的神經網絡也好,還是卷積神經網絡也好,甚至循環神經網絡也好。它們的訓練過程,以及前面的準備過程其實基本上都是差不多的,你基本上隻要去修改,怎麼樣去從輸入得到輸出就可以了。

從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社
從原理到代碼:大牛教你如何用 TensorFlow 親手搭建一套圖像識别子產品 | AI 研習社

從代碼也可以看到,開始是定義這個卷積層中的權重和偏移量,完了之後 tensorflow 會對這個卷積層有一個封裝,然後通過 conv2d 函數得到一個 2d 的卷積層,然後再把偏移量、激活函數加上去。大家可以看到整個的過程還是比較簡單的,同樣的,如果用 keras 等更進階的封裝來實作的化會更加簡單。

最後我要推薦一下《tensorflow:實戰google深度學習架構》這本書,今天講的内容,包括一些略去的内容,基本上全部在這本書裡都有非常詳細的介紹。

另外,前面提到的代碼位址如下:

代碼庫裡包含了書中所有的樣例代碼,此外還包括了才雲科技提供的 tensorflow as a service (taas) 深度學習平台的一些教程和代碼,包括後面我們做的一些圖像分類和圖像識别的樣例代碼,後面也都會陸陸續續添加進去。大家有興趣的化可以關注一下這個代碼庫。

今天的分享就到這裡,謝謝大家!

問題1:麻煩老師推薦下 coursera 的機器學習公開課?

答:吳恩達的“機器學習 machine learning”非常值得推薦的,那門課我個人至少看了兩到三遍,而且在不同的階段看都會有不同的感受。

編者按:更多機器學習的精品公開課彙總,詳見雷鋒網(公衆号:雷鋒網)相關文章“開發者入門必讀:最值得看的十大機器學習公開課”。

問題2:請問 tensorflow 相比較 keras 有什麼優勢?

答:keras 是對于 tensorflow 一個更高層的封裝,它幾乎可以實作 tensorflow 的所有功能,tensorflow 則是更底層更加靈活的一個工具,相對來說 tensorflow 的功能可能更全。但 keras 一個最大的問題在于,目前不支援分布式,我們希望 keras 在未來的版本更新中能夠加入相關的特性支援。學習的話,可以先從 keras 入手,因為它和 tensorflow 沒有本質的差別,它隻是 tensorflow 的一個高層封裝,寫起代碼來會更加友善。

問題3:ai 學習最主要的是算法和模組化對不對呀?

答:算法和模型隻是一個方面,但其實我還是比較推薦做一些實戰的應用,關鍵還是看你要做什麼事情。如果你是要做學術研究,那就要多看論文,如果你是要做工程或者要找工作的話,建議你多做一些 kaggle 的比賽。

問題4:tensorflow 在推薦系統上的運用如何?

答:tensorflow 官方有一個 wide & deep 的教程,是關于谷歌 app 推薦的一些内容,可以關注一下。tensorflow 是一個相容的架構,可以被應用在許多問題上,其實更多的是關于深度學習技術的應用,現在學術界有許多相關的研究,大家可以關注一下。

問題5:請問 tensorflow 相比較 caffe 有什麼不同?

答:tensorflow 是一個相對更全面的工具,但是在圖像處理上它的表現不如 caffe 成熟,處理速度也會稍微慢一點。tensorflow 相比 caffe 的優點是支援分布式,而且發展的速度也比 caffe 更快。

問題6:tensorflow 實質是通過大量訓練資料(監督學習)和神經網絡算法,實作深度學習過程。未來能不能不需要大量訓練資料,即非監督學習的辦法就可以實作深度學習的過程或工具,google 等巨頭有這方面的嘗試或計劃嗎?

答:非監督式學習包括增強學習其實也有嘗試,它們其實也都可以通過 tensorflow 來實作,具體怎麼做大家可以參考官網的教程。tensorflow 主要還是提供了一個計算架構,可以實作和神經網絡相關的幾乎所有算法。

問題7:tensorflow 既然支援分布式,那 tensorflow on spark 的意義還大嗎?

答:tensorflow 支援的分布式其實隻是一個計算架構,tensorflow on spark 的意義還是有的,但我覺得沒有 tensorflow on kubernetes 的意義大,spark 主要是做了一個排程和管理的系統,但是性能損失比較大,目前成熟的應用也比較少。大家如果想要了解更多分布式 tensorflow 的内容,可以關注才雲科技的平台。

問題8:我目前在用 caffe,想着要不要轉 tensorflow,老師有什麼建議麼?

答:我覺得轉 tensorflow 還是有意義的,主要還是你具體用 tensorflow 來做什麼。可能因為我接觸 tensorflow 比較多,但是我個人認為 caffe 其實正處在一個慢慢的被淘汰的邊緣。而且目前客觀上講 tensorflow 的确是一個無論在工業上還是學術上都非常流行的架構。

溫馨提示:需要原版 ppt 和視訊連結的朋友可以關注 ai 研習社公衆号(微信号:okweiwu),回複“鄭澤宇”即可。

本文作者:恒亮

繼續閱讀