利用GPU和Caffe訓練神經網絡
【編者按】 本文為利用GPU和Caffe訓練神經網絡的實戰教程,介紹了根據Kaggle的“奧托集團產品分類挑戰賽”的數據進行訓練一種多層前饋網絡模型的方法,如何將模型應用于新數據,以及如何將網絡圖和訓練權值可視化。
Caffe是由 賈揚清 發起的一個開源深度學習框架,它允許你利用你的GPU訓練神經網絡。相對于其他的深度學習框架如Theano或Torch等,Caffe不需要你自己編寫 算法程序,你只需要通過配置文件來指定網絡。顯然,這種做法比自己編寫所有程序更加節省時間,也將你限制在一定的框架范圍內。不過,在大多數情況下,這沒 有太大的問題,因為Caffe提供的框架相當強大,并且不斷進步。
這篇文章的主題由一種多層前饋網絡組成。該模型將根據Kaggle的“ 奧托集團產品分類挑戰賽 ”的數據進行訓練。我們還關注將模型應用于新數據,以及如何將網絡圖(network graph)和訓練得到的權值可視化。限于篇幅,本文不會解釋所有的細節。另外,簡單的代碼比一千多字的話更有說服力。相對于對照 IPython Notebook 來程序化細節,本文將著重描述觀念以及一些我遇到的絆腳石。
設置
如果你還沒有把Caffe安裝在你的系統上,我建議在一個允許GPU處理的EC2實例上工作,例如g2.2xlarge實例。有關如何使用EC2工作的介紹可以查看 Guide to EC2 from the Command Line ,設置Caffe及其準備工作可以參考 GPU Powered Deep Learning with NVIDIA DIGITS on EC2 。對于使用Caffe,我也建議你在你的實例上安裝IPython Notebook——在 這里 可以找到教程。
定義模型和元參數
一個模型及其應用的訓練至少需要三個配置文件。這些配置文件的格式遵循界面描述語言,稱為協議緩沖區( protocol buffers )。它表面上類似于JSON,但卻又顯著不同,實際上應該在需要進行驗證(通過自定義模式的方式——像Caffe的 這個 這樣)和序列化的數據文檔中取代它。
為了訓練,你必須有一個prototxt文件保持訓練的元參數( config.prototxt )以及一個模型用于定義網絡圖形( model_train_test.prototxt )——以非周期和定向的方式連接各層。需要注意的是,數據從底部流向到頂部時伴隨著關于怎樣指定層的順序。這里的示例網絡有五個層次:
- 數據層(一個用于訓練,一個用于測試)
- 內積層(權值Ⅰ)
- ReLUs(隱含層)
- 內積層(權值Ⅱ)
- 輸出層(用于分類的Soft Max)
A,Soft Max層給出損失
B,準確性層——允許我們看到網絡如何在訓練的同時提升。
以下從model_train_test.prototxt的摘錄顯示層(4)和(5A):
[...]
layer {
name: "ip2"
type: "InnerProduct"
bottom: "ip1"
top: "ip2"
inner_product_param {
num_output: 9
weight_filler {
type: "xavier"
}
bias_filler {
type: "constant"
value: 0
}
}
}
layer {
name: "accuracy"
type: "Accuracy"
bottom: "ip2"
bottom: "label"
top: "accuracy"
include {
phase: TEST
}
}
[...]第三個prototxt文件( model_prod.prototxt )指定應用于它的網絡。在這種情況下,它與訓練規范大體上是一致的——但它缺乏數據層(因為我們不從產品的數據源中讀取數據)并且Soft Max層不會產生損耗值但有分類的可能。另外,準確性層現在已經沒有了。還要注意的是,我們現在在開始指定輸入尺寸(如預期:1,93,1,1)——它是 肯定混亂的,所有四個尺寸被稱為input_dim,只有順序定義哪個是哪個,并沒有指定明確的背景。
支持的數據源
這是開始嘗試使用Caffe時要克服的首要心理障礙之一。它不像使用一些CSV來提供Caffe可執行的方式那樣簡單。實際上,對于沒有圖像的數據,你有三種選擇。
- LMDB(閃電內存映射數據庫)
- LevelDB
- HDF5格式
HDF5可能是最容易使用的,因為你只需要采用HDF5格式把數據集存儲到文件中。LMDB和LevelDB是數據庫,所以你必須按照他們的協 議。HDF5格式存儲數據集的大小會被內存限制,這就是為什么我拋棄它的原因。LMDB和LevelDB之間的選擇是相當隨便的——從我掠過的資源來 看,LMDB似乎更強大,速度更快,更成熟。然后從GitHub來看,LevelDB的維護似乎更積極,也具有較大的Google和 StackOverflow的足跡。
Blobs和Datums
Caffe內部使用一個叫做Blobs的數據結構進行工作,它用于正向傳遞數據和反向漸變。這是一個四維數組,其四個維度被稱為:
- N或batch_size
- 通道
- 高度
- 寬度
這與我們有關,因為在把它存儲到LMDB之前我們必須按照結構塑造我們的案例——從它被送到Caffe的地方。圖像的形狀是直觀的,一批次64個 按規定的100×200 RGB像素的圖像將最終作為形陣列(64,3,200,100)。對于一批64個特征矢量,每個長度93的Blob的形狀為(64,93,1,1)。
在將數據加載到LMDB時,你可以看到個別案例或特征向量存儲在Datum的對象上。整型數據被存儲在(字節串格式)data中,浮點型數據存儲 在float_data中。一開始我犯錯將浮點型數據分配到data中,從而導致該模型不學習任何東西。在將Datum存儲到LMDB之前,你需要將對象 序列化成一個字節的字符串表示。
總結
對我來說,掌握Caffe是一個令人驚訝的非線性體驗。也就是說,要深刻理解這個系統,還沒有任何的切入點和持續的學習路徑。讓Caffe對你發揮作用的有效信息,分布在很多不同的 教程 , GitHub上的源代碼 , IPython Notebook 以及 論壇主題 。這就是為什么我花時間撰寫本教程及相關的代碼。在我將學到的知識總結形成文本之后,我自己都要從頭讀一下。
我認為Caffe有一個光明的未來——只要添加新的功能,它將不僅僅是水平的增長,而且會垂直的重構和改善所有用戶的體驗。這絕對是高性能深度學習的好工 具。如果你想要做圖像處理和卷積神經網絡,我建議你看看NVIDIA DIGITS,它會為你提供一個舒適的GUI來實現目標。
原文鏈接: Neural Nets with Caffe Utilizing the GPU (翻譯/王瑋 責編/周建丁)