循環神經網絡驚人的有效性(下)

版權聲明:本文智能單元首發,本人原創翻譯,禁止未授權轉載。

譯者注:在CS231n課程筆記止步於CNN,沒有循環神經網絡(RNN和LSTM),實爲憾事。經知友推薦,將The Unreasonable Effectiveness of Recurrent Neural Networks一文翻譯完畢,作爲補充。感謝@猴子的校對。

目錄

  • 循環神經網絡
  • 字母級別的語言模型
  • RNN的樂趣
    • Paul Graham生成器
    • 莎士比亞
    • 維基百科
    • 幾何代數
    • Linux源碼
    • 生成嬰兒姓名
  • 理解訓練過程 譯者注:下篇起始處
    • 訓練時輸出文本的進化
    • RNN中的預測與神經元激活可視化
  • 源代碼
  • 拓展閱讀
  • 結論
  • 譯者反饋

理解訓練過程

我們已經看見訓練結束後的結果令人印象深刻,但是它到底是如何運作的呢?現在跑兩個小實驗來一探究竟。

訓練時輸出文本的進化

首先,觀察模型在訓練時輸出文本的不斷進化是很有意思的。例如,我使用托爾斯泰的《戰爭與和平》來訓練LSTM,並在訓練過程中每迭代100次就輸出一段文本。在第100次迭代時,模型輸出的文本是隨機排列的:

tyntd-iafhatawiaoihrdemot  lytdws  e ,tfti, astai f ogoh eoase rrranbyne 'nhthnee e 
plia tklrgd t o idoe ns,smtt   h ne etie h,hregtrs nigtike,aoaenns lng

但是至少可以看到它學會了單詞是被空格所分割的,只是有時候它使用了兩個連續空格。它還沒學到逗號後面總是有個空格。在迭代到第300次的時候,可以看到模型學會使用引號和句號。

"Tmont thithey" fomesscerliund
Keushey. Thom here
sheulke, anmerenith ol sivh I lalterthend Bleipile shuwy fil on aseterlome
coaniogennc Phe lism thond hon at. MeiDimorotion in ther thize."

單詞被空格所分割,模型開始知道在句子末尾使用句號。在第500次迭代時:

we counter. He stutn co des. His stanted out one ofler that concossions and was 
to gearang reay Jotrets and with fre colt otf paitt thin wall. Which das stimn 

模型開始學會使用最短和最常用的單詞,比如“we”、“He”、“His”、“Which”、“and”等。從第700次迭代開始,可以看見更多和英語單詞形似的文本:

Aftair fall unsuch that the hall for Prince Velzonski's that me of
her hearly, and behs to so arwage fiving were to it beloge, pavu say falling misfort 
how, and Gogition is so overelical and ofter.

在第1200次迭代,我們可以看見使用引號、問好和感嘆號,更長的單詞也出現了。

"Kite vouch!" he repeated by her
door. "But I would be done and quarts, feeling, then, son is people...."

在迭代到2000次的時候,模型開始正確的拼寫單詞,引用句子和人名。

"Why do what that day," replied Natasha, and wishing to himself the fact the
princess, Princess Mary was easier, fed in had oftened him.
Pierre aking his soul came to the packs and drove up his father-in-law women.

從上述結果中可見,模型首先發現的是一般的單詞加空格結構,然後開始學習單詞;從短單詞開始,然後學習更長的單詞。由多個單詞組成的話題和主題詞要到訓練後期纔會出現。

RNN中的預測與神經元激活可視化

另一個有趣的實驗內容就是將模型對於字符的預測可視化。下面的圖示是我們對用維基百科內容訓練的RNN模型輸入驗證集數據(藍色和綠色的行)。在每個字母下面我們列舉了模型預測的概率最高的5個字母,並用深淺不同的紅色着色。深紅代表模型認爲概率很高,白色代表模型認爲概率較低。注意有時候模型對於預測的字母是非常有信心的。比如在http://www. 序列中就是。

輸入字母序列也被着以藍色或者綠色,這代表的是RNN隱層表達中的某個隨機挑選的神經元是否被激活。綠色代表非常興奮,藍色代表不怎麼興奮。LSTM中細節也與此類似,隱藏狀態向量中的值是[-1, 1],這就是經過各種操作並使用tanh計算後的LSTM細胞狀態。直觀地說,這就是當RNN閱讀輸入序列時,它的“大腦”中的某些神經元的激活率。不同的神經元關注的是不同的模式。在下面我們會看到4種不同的神經元,我認爲比較有趣和能夠直觀理解(當然也有很多不能直觀理解)。

————————————————————————————————————————

本圖中高亮的神經元看起來對於URL的開始與結束非常敏感。LSTM看起來是用這個神經元來記憶自己是不是在一個URL中。

——————————————————————————————————————————

高亮的神經元看起來對於markdown符號[[]]的開始與結束非常敏感。有趣的是,一個[符號不足以激活神經元,必須等到兩個[[同時出現。而判斷有幾個[的任務看起來是由另一個神經元完成的。

——————————————————————————————————————————

這是一個在[[]]中線性變化的神經元。換句話說,在[[]]中,它的激活是爲RNN提供了一個以時間爲準的座標系。RNN可以使用該信息來根據字符在[[]]中出現的早晚來決定其出現的頻率(也許?)。

——————————————————————————————————————————

這是一個進行局部動作的神經元:它大部分時候都很安靜,直到出現www序列中的第一個w後,就突然關閉了。RNN可能是使用這個神經元來計算www序列有多長,這樣它就知道是該輸出有一個w呢,還是開始輸出URL了。

——————————————————————————————————————————

當然,由於RNN的隱藏狀態是一個巨大且分散的高維度表達,所以上面這些結論多少有一點手動調整。上面的這些可視化圖片是用定製的HTML/CSS/Javascript實現的,如果你想實現類似的,可以查看這裏

我們可以進一步簡化可視化效果:不顯示預測字符僅僅顯示文本,文本的着色代表神經元的激活情況。可以看到大部分的細胞做的事情不是那麼直觀能理解,但是其中5%看起來是學到了一些有趣並且能理解的算法:

—————————————————————————————————————————

—————————————————————————————————————————

在預測下個字符的過程中優雅的一點是:我們不用進行任何的硬編碼。比如,不用去實現判斷我們到底是不是在一個引號之中。我們只是使用原始數據訓練LSTM,然後它自己決定這是個有用的東西於是開始跟蹤。換句話說,其中一個單元自己在訓練中變成了引號探測單元,只因爲這樣有助於完成最終任務。這也是深度學習模型(更一般化地說是端到端訓練)強大能力的一個簡潔有力的證據。

源代碼

我想這篇博文能夠讓你認爲訓練一個字符級別的語言模型是一件有趣的事兒。你可以使用我在Github上的char rnn代碼訓練一個自己的模型。它使用一個大文本文件訓練一個字符級別的模型,可以輸出文本。如果你有GPU,那麼會在比CPU上訓練快10倍。如果你訓練結束得到了有意思的結果,請聯繫我。如果你看Torch/Lua代碼看的頭疼,別忘了它們只不過是這個100行項目的高端版。

題外話。代碼是用Torch7寫的,它最近變成我最愛的深度學習框架了。我開始學習Torch/LUA有幾個月了,這並不簡單(花了很多時間學習Github上的原始Torch代碼,向項目創建者提問來解決問題),但是一旦你搞懂了,它就會給你帶來很大的彈性和加速。之前我使用的是Caffe和Theano,雖然Torch雖然還不完美,但是我相信它的抽象和哲學層次比前兩個高。在我看來,一個高效的框架應有以下特性:

  • 有豐富函數(例如切片,數組/矩陣操作等)的,對底層CPU/GPU透明的張量庫。
  • 一整個基於腳本語言(比如Python)的分離的代碼庫,能夠對張量進行操作,實現所有深度學習內容(前向、反向傳播,計算圖等)。
  • 分享預訓練模型非常容易(Caffe做得很好,其他的不行)。
  • 最關鍵的:沒有編譯過程!或者至少不要像Theano現在這樣!深度學習的趨勢是更大更復雜的網絡,這些網絡都有隨着時間展開的複雜計算流程。編譯時間不能太長,不然開發過程將充滿痛苦。其次,編譯導致開發者放棄解釋能力,不能高效地進行調試。如果在流程開發完成後有個選項能進行編譯,那也可以。

拓展閱讀

在結束本篇博文前,我想把RNN放到更廣的背景中,提供一些當前的研究方向。RNN現在在深度學習領域引起了不小的興奮。和卷積神經網絡一樣,它出現已經有十多年了,但是直到最近它的潛力才被逐漸發掘出來,這是因爲我們的計算能力日益強大。下面是當前的一些進展(肯定不完整,而且很多工作可以追溯的1990年):

在NLP/語音領域,RNN將語音轉化爲文字,進行機器翻譯,生成手寫文本,當然也是強大的語言模型 (Sutskever等) (Graves) (Mikolov等)。字符級別和單詞級別的模型都有,目前看來是單詞級別的模型更領先,但是這只是暫時的。

計算機視覺。RNN迅速地在計算機視覺領域中被廣泛運用。比如,使用RNN用於視頻分類圖像標註(其中有我自己的工作和其他一些),視頻標註和最近的視覺問答。在計算機視覺領域,我個人最喜歡的RNN論文是《Recurrent Models of Visual Attention》,之所以推薦它,是因爲它高層上的指導方向和底層的建模方法(對圖像短時間觀察後的序列化處理),和建模難度低(REINFORCE算法規則是增強學習裏面策略梯度方法中的一個特例,使得能夠用非微分的計算來訓練模型(在該文中是對圖像四周進行快速查看))。我相信這種用CNN做原始數據感知,RNN在頂層做快速觀察策略的混合模型將會在感知領域變得越來越流行,尤其是在那些不單單是對物體簡單分類的複雜任務中將更加廣泛運用。

歸納推理,記憶和注意力(Inductive Reasoning, Memories and Attention)。另一個令人激動的研究方向是要解決普通循環網絡自身的侷限。RNN的一個問題是它不具有歸納性:它能夠很好地記憶序列,但是從其表現上來看,它不能很好地在正確的方向上對其進行歸納(一會兒會舉例讓這個更加具體一些)。另一個問題是RNN在運算的每一步都將表達數據的尺寸和計算量聯繫起來,而這並非必要。比如,假設將隱藏狀態向量尺寸擴大爲2倍,那麼由於矩陣乘法操作,在每一步的浮點運算量就要變成4倍。理想狀態下,我們希望保持大量的表達和記憶(比如存儲全部維基百科或者很多中間變量),但同時每一步的運算量不變。

在該方向上第一個具有說服力的例子來自於DeepMind的神經圖靈機(Neural Turing Machines)論文。該論文展示了一條路徑:模型可以在巨大的外部存儲數組和較小的存儲寄存器集(將其看做工作的存儲器)之間進行讀寫操作,而運算是在存儲寄存器集中進行。更關鍵的一點是,神經圖靈機論文提出了一個非常有意思的存儲解決機制,該機制是通過一個(soft和全部可微分的)注意力模型來實現的。譯者注:這裏的soft取自softmax。基於概率的“軟”注意力機制(soft attention)是一個強有力的建模特性,已經在面向機器翻譯的《 Neural Machine Translation by Jointly Learning to Align and Translate》一文和麪向問答的《Memory Networks》中得以應用。實際上,我想說的是:

注意力概念是近期神經網絡領域中最有意思的創新。

現在我不想更多地介紹細節,但是軟注意力機制存儲器尋址是非常方便的,因爲它讓模型是完全可微的。不好的一點就是犧牲了效率,因爲每一個可以關注的地方都被關注了(雖然是“軟”式的)。想象一個C指針並不指向一個特定的地址,而是對內存中所有的地址定義一個分佈,然後間接引用指針,返回一個與指向內容的權重和(這將非常耗費計算資源)。這讓很多研究者都從軟注意力模式轉向硬注意力模式,而硬注意力模式是指對某一個區域內的內容固定關注(比如,對某些單元進行讀寫操作而不是所有單元進行讀寫操作)。這個模型從設計哲學上來說肯定更有吸引力,可擴展且高效,但不幸的是模型就不是可微分的了。這就導致了對於增強學習領域技術的引入(比如REINFORCE算法),因爲增強學習領域中的研究者們非常熟悉不可微交互的概念。這項工作現在還在進展中,但是硬注意力模型已經被髮展出來了,在《 Inferring Algorithmic Patterns with Stack-Augmented Recurrent Nets》,《 Reinforcement Learning Neural Turing Machines》,《Show Attend and Tell》三篇文章中均有介紹。

研究者。如果你想在RNN方面繼續研究,我推薦Alex GravesIlya SutskeverTomas Mikolov三位研究者。想要知道更多增強學習和策略梯度方法(REINFORCE算法是其中一個特例),可以學習David Silver的課程,或Pieter Abbeel的課程

代碼。如果你想要繼續訓練RNN,我聽說Theano上的keraspassage還不錯。我使用Torch寫了一個項目,也用numpy實現了一個可以前向和後向傳播的LSTM。你還可以在Github上看看我的NeuralTalk項目,是用RNN/LSTM來進行圖像標註。或者看看Jeff Donahue用Caffe實現的項目。

結論

我們已經學習了RNN,知道了它如何工作,以及爲什麼它如此重要。我們還利用不同的數據集將RNN訓練成字母級別的語言模型,觀察了它是如何進行這個過程的。可以預見,在未來將會出現對RNN的巨大創新,我個人認爲它們將成爲智能系統的關鍵組成部分。

最後,爲了給文章增添一點格調,我使用本篇博文對RNN進行了訓練。然而由於博文的長度很短,不足以很好地訓練RNN。但是返回的一段文本如下(使用低的溫度設置來返回更典型的樣本):

I've the RNN with and works, but the computed with program of the 
RNN with and the computed of the RNN with with and the code

是的,這篇博文就是講RNN和它如何工作的,所以顯然模型是有用的:)下次見!

譯者反饋

  1. 翻譯不到位的地方,歡迎知友們評論批評指正;
  2. 關於Torch和TensorFlow,AK本人現在在OpenAI工作主要是在用TF了,但是他對於Torch還是有很強的傾向性。這在他最新的博文中可以看到;
  3. 在計算機視覺方面,個人對於圖像標註比較感興趣,正在入坑。歡迎有同樣興趣的知友投稿討論;
  4. 想要加入翻譯小組的同學,請連續3次在評論中對我們最新的翻譯做出認真的批評和指正,而後我們會小組內投票決定是否吸納新成員:)這個小小的門檻是爲了方便我們找到真正喜愛機器學習和翻譯的同學。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章