b大的深度學習框架有什麼獨到之處?

它使用了J語言,可以自動求導,不需要LAYER的概念,支持RANK(雖然是一個NP問題),他是否要超過CAFFE(基於C++), TORCH(基於LUA)等落伍的語言框架?

Rolling your own neural network framework

怎麼看待長江後浪推前浪的現象。


一切在於粗粒度和細粒度操作之爭, @bhuztez 的做法是把一些操作轉化成細粒度操作,然後直接優化。傳統方法更多注重粗粒度或者粗粒度和細粒度混合的做法。

細粒度理論上有更好的表示一般性,粗粒度比較適合特殊優化幾個常見瓶頸。

- 粗粒度的好處本身是做特殊瓶頸優化容易,比如如果有 conv-activation直接手寫一個東西優化掉,現在的cuDNN基本也是這樣。類似的,把一些常見操作的導數寫到一起。 相對來說的壞處沒有細粒度的內存等優化,只要在數量級上面沒有差別基本沒沒差。

- 細粒度的表示理論上可以通過編譯優化做很多事情,但是其實如果用細粒度操作和已經有的技術讓編譯器自動在GPU上面去優化一個卷積依然還是做不好。當然細粒度操作在elementwise一類的簡單操作上面做RTC基本沒有問題。

所以全部細粒度的路線雖然在理論上有更多優化空間,但是因為損失了粗粒度的信息,反而不容易直接做一些粗粒度的優化。比如直接把conv-activation合併成一個手寫函數在粗粒度表示上面容易,雖然只優化了這一個,但是這一個東西在常見場景中出現,可以優化的好就夠了。

另外layer的fp, bp介面並非一無是處。很多時候用戶需要imperative 執行的時候,layer和bp的介面可以比較自然地把多個網路串起來。當然並不是說著自動求導不可以串聯,總結起來,自動求導適合於所有操作都可自動求導的情況,而fp/bp 介面適合需要插入用戶自定義代碼和用戶手工串聯的情況。手工串聯的情況的例子有不少:在CNN 上面加 CRF誤差函數, 對抗網路等。

總結一下,在手工優化還是需要存在的今天,需要效率為重的深度學習依然還是會需要粗粒度操作。支持各個方法在它們合適的場景混用才是比較實在的解決方案。


曾博在時,我已悉數告知。你怎麼還要提問,一看你就是冒充的,並不是真正的魂靈勃勃。還有不要傳播謠言

1. 並沒有使用J語言

2. 這個rank連問題都不是,哪裡來的NP-complete與否?

3. 從對框架該怎麼造的認識上講,LiFT起點就在Caffe什麼的前面,又怎麼能超越Caffe呢?要想超越Caffe,首先要Caffe超越LiFT才行。

----------------------

這個教程最最重要的只是告訴你,自製框架完全是可行的。現有的框架完全不值得一用。

比如你看這個問題請問如何將深度學習Caffe做成一個動態庫,方便在其他應用程序中調用? 你用LiFT這種思路搞,就問不出來這個問題了。畢竟你想生成什麼代碼就生成什麼代碼,直接生成一段C代碼,你愛怎麼鏈接就怎麼鏈接。就為了幾十行C代碼,去搞什麼"功能強大的cmake支持"完全沒有必要啊。因為直接生成C代碼了,我也不用管你怎麼讀寫文件了,你愛用什麼格式用什麼格式。LiFT使用Python單純只是因為有個現成的binding。

第二,有人吐槽過這個教程里自動求導還是用的是backpropagation。這個主要是為了適應教程的寫法。因為教程里先寫怎麼解釋,後寫怎麼編譯。假如有人腦洞大開,直接在解釋執行那裡就把oblique什麼的加進去,內存就爆了。比如輸入僅僅是 25x25x3x3 ,輸出是27x27,那麼25*25*3*3*27*27*8 = 32805000,也就是假如用雙精度浮點數,不管你怎麼省,僅僅這一個jacobian就至少要用32M內存,裡面還全是0和1。而編譯時,藉助integer set library和編譯期計算,這個jacobian是可以消掉的。

同時你也要注意到,即便同樣只是backpropagation,LiFT實現起來要比比如Caffe容易多了。Caffe里,你加個新的layer forward/backward全都要你自己實現,也就是backward需要你自己先把導數算出來。而在LiFT里不存在這個問題,只有在你新加入像sin, cos這種基本函數時,才需要提供導數,基本函數的導數公式直接無腦抄過來就好,並不需要你自己去算啊。

所以你看到了,layer反而讓實現變麻煩了。看RGB圖像在CNN中如何進行convolution? - lixin liu 的回答,你就知道這種按layer套layer思路來實現的框架往往model里還省略了不少參數,讓model變得不容易看懂了。還動不動要自己寫個新的layer,大家是否認為自動梯度+小顆粒度操作符將是深度學習框架的主流? ,假如CuDNN里不提供對應的實現,跑分肯定不行。

光有多維數組而沒有rank,寫起程序來非常麻煩。在numpy中是否有什麼辦法擴展dot函數? - 知乎用戶的回答中你可以看到,有了rank,在numpy中需要去找一個現成的函數或者自己用循環來實現的問題,可以通過rank套rank輕易解決。這也極大的簡化了自動求導的實現,你看autograd,需要搞一個tape來支持循環等各種控制結構,各種現有的函數也要自己去包一遍,這個工作量是驚人的。

而mxnet不用integer set library而是自己拍腦袋實現了消數組的功能,所謂的symbolic api還是搞成了差不多按layer劃分的方式。因為mxnet這樣瞎搞是沒法精確到數組中每個元素的使用情況的,能消去的數組非常有限。LiFT因為採用了傳統的做法,而不是自己拍腦袋瞎搞一套出來,所以在消中間數組上能走的更遠,這也順便使得跳出layer的束縛成為可能。這就是為什麼LiFT的model里可以把矩陣點乘,拆分成乘法和加法兩個步驟來算的原因。

這個教程告訴我們,尊重常識,不要自己瞎搞,只要做一點微小工作,就可以造出好用的深度學習框架了。然而曾博終究還是去學C++了。


曾老師怎麼可能會用b大來稱呼bhuztez?曾老師一般都是念成

快說,是不是曾老師本人?


推薦閱讀:

能否使用區塊鏈的算力來解決深度學習訓練?
目前,人工智慧語音在說中文時的語氣感覺上還比較機械,怎樣使人工智慧語音的語氣更自然一些?
theano中怎麼查看TensorVariable的值,在debug時如何跟蹤這樣的變數?
是不是對於任意 n×n 大小的圍棋棋盤,人類都贏不了 AlphaGo Zero 了?

TAG:深度學習DeepLearning | Caffe深度學習框架 | Torch深度學習框架 |