編者按:此前,論智曾寫過一篇Kaggle競賽方案分享:如何分辨雜草和植物幼苗,介紹了當時排名第五的開發者Kumar Shridhar的實戰思路。同樣是這個競賽,自參賽起,fast.ai聯合創始人Jeremy Howard的名次卻經歷連連暴跌,最后止步第105名。那么這位明星數據科學家究竟遭遇了何方狙擊?沒錯,就是他自己的學生,而這些新手最后也成功霸榜Kaggle。
當我離開你時,我只是求學者,但現在,我才是王者
隨著互聯網和知識傳播的深度結合,現在在線課程對許多人來說已經不是新鮮事物,在深度學習領域,最受學生歡迎的MOOC課程平臺有三個:Fast.ai、deeplearning.ai /Coursera和Udacity。其中,因為Jeremy Howard化繁為簡、實戰為上的獨特授課風格,Fast.ai給人的印象一直很“接地氣”,而植物幼苗分類賽的結果也證實了課程的教學效果。
那么這些新手在短短幾周內就學會使用頂級算法的秘訣是什么?是什么讓他們能在競賽中擊敗擁有大量GPU的資深深度學習專家?下文是你想知道的所有答案。
如果你已經上手深度學習,并希望快速了解Fast.ai課程中使用的強大技術,請繼續閱讀。 如果你已經完成Fast.ai課程,并希望回顧所學內容,請繼續閱讀。 如果你正準備入門深度學習,并希望了解Fast.ai對初學者的幫助和這個行業的未來發展,請繼續閱讀。
首先,在正式開始前,我們都應該知道,如果要有效學習Fast.ai的課程內容,云GPU必不可少。這里我們先介紹一個好用的工具——FloydHub,對于初學者來說,這是訓練深度學習模型最好的、也是最簡單的方法。法國的Ecole 42非常喜愛這個工具,我們也可以借此為接觸更多有趣實現做準備,如:
如何用100行神經網絡代碼為黑白圖片著色
如何用深度學習做“前端”:基于設計模型圖片生成HTML和CSS代碼
下面,讓我們正式開始!
1. 使用Fast.ai庫
from fast.ai import *
Fast.ai庫不僅是讓新手快速構建深度學習實現的工具包,它也是提供最佳實踐的一個強大而便捷的資源。每當Fast.ai團隊(包括AI研究人員和合作者網絡)發現一篇特別有趣的論文,他們就會在各種數據集上測試,然后找出調整優化方法。如果這些成果確實是有效的,它們會陸續出現在庫中,以便用戶快速接觸新技術。
這樣做的結果是Fast.ai庫現在已經成為一個功能強大的工具箱,比如去年學界公認的深度學習年度進展:SGDR、循環學習,現在所有Fast.ai用戶都可以快速訪問,并把它們用于自己的實現。
這個庫基于PyTorch構建,使用流暢,用戶體驗很好。
2. 使用多個學習率,而不是一個
使用不同的學習率意味著在訓練期間,神經網絡前幾層的變化比后幾層更多。在計算機視覺任務中,現在通行的一種做法是直接在現有架構上構建深度學習模型,實踐證明這樣做模型的性能更好。
而大多數架構,如Resnet、VGG、inception等都是在ImageNet上經過預訓練的,如果要使用它們,我們必須考量手頭數據集和ImageNet圖像的相似程度,并以此對權重做或多或少的調整。在修改權重時,模型的最后幾層調整幅度更大,而用于檢測基礎特征的層(比如邊緣和輪廓)則只需極少調整。
下面是一些代碼示例,首先,我們從Fast.ai庫里獲得預訓練模型:
from fastai.conv_learner import *
# 導入用于創建卷積學習對象的庫 #選擇VVG16
# 將模型分配給resnet、vgg,甚至是你自己的自定義模型
PATH = './folder_containing_images'
data = ImageClassifierData.from_paths(PATH)
# 創建fast ai數據對象,這里我們用from_paths
# 其中PATH將每個圖像類分成不同的文件夾
learn = ConvLearner.pretrained(model, data, precompute=True)
# 創建一個學習對象,以便快速調用Fast.ai庫里的state of art算法
通過創建好的學習對象,我們可以凍結最后一層以前的所有層,單獨調整最后一層的參數:
learn.freeze()
# 凍結最后一層之前的所有層,保持它們的參數不變
learning_rate = 0.1
learn.fit(learning_rate, epochs=3)
# 只訓練最后一層幾個epoch
如果調參結果不錯,我們就可以在不同層使用不同的學習率,比如中間幾層參數變化幅度沒最后幾層那么大,所以它的學習率可以是后者的1/10。
learn.unfreeze()
# 將所有圖層的requires_grads設置為True,以便進行更新
learning_rate = [0.001, 0.01, 0.1]
# first layer的學習率是0.001,middle layer的是0.01,final layer則是0.1.
learn.fit(learning_rate, epochs=3)
# 用不同學習率訓練模型三個epoch
3. 如何找到合適的學習率
學習率是訓練神經網絡最重要的一個超參數,但直到最近,許多人才發現以前設置學習率的方式非常不當。去年,Leslie N. Smith在arXiv上提交了一個預印本:Cyclical Learning Rates for Training Neural Networks。他在文中提出一種確定學習率的新方法:循環學習率,即不使用固定值,而是用一個在合理閾值內循環變化的數值,實驗證明它可以減少迭代次數,提高模型分類準確率。文章一經發布,Fast.ai就立馬推廣了這種方法。
對于這種方法,我們可以從一個較低的學習率開始訓練神經網絡,然后隨著迭代進行,逐漸對學習率做指數增加。以下是示例代碼:
learn.lr_find()
# 隨著學習率呈指數增長,訓練學習對象
learn.sched.plot_lr()
# 繪制學習率和迭代的進展圖
學習率隨迭代呈指數上升
同時,記錄不同學習率時每個值的損失,并繪制相關圖像:
learn.sched.plot()
# 學習率和損失的關系圖
損失一直在減少,還沒有穩定
在上圖情況下,我們可以確定的最佳學習率是0.01。
4. 余弦退火
隨著每個batch隨機梯度下降(SGD)的進行,神經網絡的損失會逐漸接近全局最小值,相應的,學習率也應該變得更小,防止算法超調。余弦退火是一種將學習率設置為隨模型迭代輪數不斷改變的方法,因為更新學習率用的是cos(),所以稱余弦。如下圖所示:
隨著x增加,cos(x)會不斷縮小
當我們不斷增加x時,cos(x)的變化是一個先緩慢后急劇再緩慢的過程,這種下降趨勢十分符合學習率,因此也可以提高模型性能。
learn.fit(0.1, 1)
# 在Fast.ai庫中調用learn.fit函數可以直接使用余弦退火
5. SGDR
在訓練期間,梯度下降可能會陷入局部最小值而不是全局最小值。
梯度下降可能會陷入局部最小值
這時,通過突然提高學習率,梯度下降可以“跳出”局部最小值,重新回歸尋找全局最小值的正軌。這種方法被稱為熱重啟隨機梯度下降(SGDR),它首次出現在德國弗萊堡大學的論文SGDR: Stochastic Grandient Descent with warm Restarted中,這也是ICLR 2017的重磅成果。
現在,SGDR已經加入Fast.ai庫,當用戶調用learn.fit(learning_rate, epochs)時,每個epoch的學習率會被重新設置成原始超參數,然后在用余弦退火逐漸縮小。
每個epoch的學習率回歸原始值
每次學習率下降到最低點,我們就稱之為一個循環。
cycle_len = 1
# 決定學習率降到最低要幾個epoch
# 在這種情況下,1個epoch
cycle_mult=2
# 在每個循環結束時,將cycle_len值乘以2
learn.fit(0.1, 3, cycle_len=2, cycle_mult=2)
# 在這種情況下,將重啟3次
# 第一次的cycle_len為1,所以我們用1個epoch完成循環
# cycle_mult=2,所以下個循環是2個epoch
# 然后是4個epoch,以此類推
每個循環所需epoch是上個循環的兩倍
使用這種方法可以幫助開發者在圖像分類問題中占據先機。
6. 把激活函數想象成人
Softmax是一個專一的家伙,只喜歡挑選一個目標;Sigmoid只想知道你在-1和1之間的位置,如果超出了閾值,他才不管你的死活;Relu是一名稱職的夜店門衛,如果顏值為負,你就別想過這道門。
以上述方式看待激活函數縱然有點蠢,但至少它區分了三種函數的不同,可以有效防止誤用。Jeremy Howard曾表示,他在許多學術論文中都看到過把Softmax用于多元分類,而文章、博客中的激活函數濫用更不鮮見。
7. 遷移學習對NLP任務非常有用
眾所周知,遷移學習在計算機視覺中的效果非常出色,而隨著研究人員的不斷探索,如今越來越多線索開始指向另一個現實:自然語言處理(NLP)模型同樣能從遷移學習中收益頗多。
在fast.ai的第4課中,Jeremy Howard構建了一個用于分類IMDB電影評論消極與否的模型,他把遷移學習思想引入模型,發現模型的準確率遠超Bradbury等人的最先進成果,效果立竿見影。
他加入了一個預訓練模型
而這個做法的成功秘訣是先訓練一個模型,讓它對語言產生基礎理解,然后再把這個預訓練模型作為模型的一部分用于情感分析。為了構建這第一個模型,我們需要讓RNN學會預測文本序列中的下一個詞,也就是語言建模。一旦模型訓練完畢,性能很好,第二個新模型就能利用它對每個次的編碼分析影評是積極的還是消極的。
雖然課程示例是個情感分析模型,但我們也可以把它用到其他NLP和計算機視覺任務中。
8. 用深度學習處理結構化數據
在介紹機器學習和深度學習優勢時,我們一般會夸它們可以處理非結構化數據,認為這是統計學無法做到的,但Fast.ai反其道而行之,他們用深度學習實現了在結構化數據上快速生成出色結果,而無需借助特征工程和應用領域的特定知識。
他們的庫充分利用了PyTorch的嵌入功能,允許將分類變量快速轉換為嵌入矩陣。當然,課程中展示的技術相對較簡單,只是將分類變量轉換為數字,然后為每個值分配嵌入向量:
為一周中的每一天嵌入4個值
與創建虛擬變量(one-hot編碼)的傳統方法相比,這樣做的好處是對于每一天,我們可以用4個值代替一個值,從而創建維度更高、更豐富的矩陣。
9. 競賽致勝關鍵:擴大圖像尺寸、Dropout和TTA
4月30日,在斯坦福大學舉辦的DAWNBench中,fast.ai團隊一舉贏得Imagenet和CIFAR10分類競賽,之后Jeremy Howard寫了一篇獲勝感言,他把競賽結果歸功于fast.ai庫中的一些獨特工具。
兩年前Geoffrey Hinton提出的Dropout是其中之一。盡管論文發布之初,學界對這個概念十分追捧,但它在計算機視覺領域卻一直不受重視。幸好,現在有了PyTorch,如果我們用PyTorch實現Dropout,它會變得異常簡單,而如果用了fast.ai庫,整個過程就更簡單了。
空格表示Dropout函數激活的區域
Dropout可以很好地防止模型過擬合,這對于在CIFAR10這樣的小型數據集上構建分類器是非常重要的。在創建學習對象時,fast.ai會自動執行Dropout,但它可以自定義修改:
learn = ConvLearner.pretrained(model, data, ps=0.5, precompute=True)
# 在測試集上創建0.5的Dropout(激活的一半)
# 驗證集會自動關閉此功能
除此之外,他們采用的另一種方法是先在較小的圖像上訓練,然后擴大圖像尺寸,在用相同的模型在上面訓練。這樣做可以有效防止過擬合,同時提高模型性能。
# create a data object with images of sz * sz pixels
def get_data(sz):
tmfs = tfms_from_model(model, sz)
# tells what size images should be, additional transformations such
# image flips and zooms can easily be added here too
data = ImageClassifierData.from_paths(PATH, tfms=tfms)
# creates fastai data object of create size
return data
learn.set_data(get_data(299))
# changes the data in the learn object to be images of size 299
# without changing the model.
learn.fit(0.1, 3)
# train for a few epochs on larger versions of images, avoiding overfitting
最后一種方法則是測試時數據增強(TTA),也就是把測試集里的原始圖像做裁剪、縮放,轉換成一系列不同的圖像,然后用于圖像測試。這之后,我們計算不同版本的平均輸出,并將其作為圖像的最終分數,這可以通過調用learn.TTA()直接實現:
preds, target = learn.TTA()
10. 創造力是關鍵
fast.ai團隊不僅在DAWNBench競賽中贏得了訓練速度最快獎(3小時),也把成本壓縮到25美元,堪稱奇跡。這里我們可以學到的經驗是,創建一個成功的深度學習模型并不意味著投入更多GPU,創造力、想法和創新可以為我們打開另一扇窗。
本文提到的大多數學術突破也是創造力的一個佐證,當別人用千篇一律的做法解決問題時,這些學者想到了不同的方法,而且這些創新確實有效。雖然硅谷的大公司擁有海量GPU,這是常人不敢奢望的,但我們要勇于發起挑戰,創造出屬于自己的特殊的、新的東西。
有時候,現實的擠壓也是一種機遇,畢竟必要性是成功之母。
-
神經網絡
+關注
關注
42文章
4781瀏覽量
101176 -
算法
+關注
關注
23文章
4630瀏覽量
93360 -
深度學習
+關注
關注
73文章
5516瀏覽量
121553
原文標題:從fast.ai學到的十大技巧:如何在幾周內上手頂級算法
文章出處:【微信號:jqr_AI,微信公眾號:論智】歡迎添加關注!文章轉載請注明出處。
發布評論請先 登錄
相關推薦
評論