多任务学习方法
??最近一直在做多任務,但是效果好象沒什么提升,因為都是憑自己的想法和感覺在做。于是上網查找了一些這方面的資料,尋求一些理論上的支撐和前人經驗上的幫助。
多任務學習:
??故名思意,就是多個任務一起學習。為什么要進行多任務學習呢?因為現實中樣本采樣的成本較高,而訓練樣本不足常常會出現過擬合的現象,而將多個相關任務同時學習,通過共享某個共同的知識可以提高各任務的泛化效果。
分類:
??基于軟共享的深度多任務學習
??基于硬共享的深度多任務學習
一些問題:
1、損失的整合
??為多個任務定義一個損失函數,若將每個任務的損失進行簡單相加,由于不同任務的收斂速度不同,可能某一任務的收斂得到不錯的效果,而其他任務表現卻很差。
??簡單的解決辦法是將簡單相加變為加權相加,但這樣會不時進行調參。
??論文《Multi-Task Learning Using Uncertainty to Weigh Losses for Scene Geometry and Semantics》,提出引入不確定性來確定損失的權重:在每個任務的損失函數中學習另一個噪聲參數(noise parameter)。此方法可以接受多任務(可以是回歸和分類),并統一所有損失的尺度。這樣就能像一開始那樣,直接相加得到總損失了。該方法不僅可以得到很好的結果而且不需要考慮額外的權重超參數。
2、調節學習速率
??學習速率是最重要的超參數之一。我們發現,任務 A 和任務 B 各自合適的速率可能是不同的。這時,我們可以在各個任務的子網絡(基于硬共享的深度多任務學習)分別調節各自的學習速率,而在共享網絡部分,使用另一個學習速率。
??雖然聽上去很復雜,但其實非常簡單。通常,在利用 TensorFlow 訓練神經網絡時,使用的是:
??AdamOptimizer 定義如何應用梯度,而 minimize 則完成具體的計算和應用。我們可以將 minimize 替換為我們自己的實現方案,在應用梯度時,為計算圖中的各變量使用各自適合的學習速率。
all_variables = shared_vars + a_vars + b_vars all_gradients = tf.gradients(loss, all_variables)shared_subnet_gradients = all_gradients[:len(shared_vars)] a_gradients = all_gradients[len(shared_vars):len(shared_vars + a_vars)] b_gradients = all_gradients[len(shared_vars + a_vars):]shared_subnet_optimizer = tf.train.AdamOptimizer(shared_learning_rate) a_optimizer = tf.train.AdamOptimizer(a_learning_rate) b_optimizer = tf.train.AdamOptimizer(b_learning_rate)train_shared_op = shared_subnet_optimizer.apply_gradients(zip(shared_subnet_gradients, shared_vars)) train_a_op = a_optimizer.apply_gradients(zip(a_gradients, a_vars)) train_b_op = b_optimizer.apply_gradients(zip(b_gradients, b_vars))train_op = tf.group(train_shared_op, train_a_op, train_b_op)注:這個技巧其實在單任務網絡中也很實用
3、將估計作為特征
??當完成第一階段的工作,為預測多任務創建好神經網絡后,我們可能希望將某一個任務得到的估計(estimate)作為另一個任務的特征。在前向傳遞(forward-pass)中,這非常簡單。但在反向傳播中呢?
??假設將任務 A 的估計作為特征輸入給 B,我們可能并不希望將梯度從任務 B 傳回任務 A,因為我們已經有了任務 A 的標簽。對此,TensorFlow 的 API 所提供的 tf.stop_gradient 會有所幫助。在計算梯度時,它允許你傳入一個希望作為常數的張量列表,這正是我們所需要的。
不止如此,該技術可用在任何你希望利用 TensorFlow 計算某個值并將其作為常數的場景。
我的一些想法:
關于多個任務的訓練,應該也可以不統一成一個損失函數,各個任務擁有自己的損失函數即可。
這樣可以分別找到適合各個任務的學習速率,和迭代次數,然后進行次數不同迭代即可。
比如:
任務A需要迭代100次才收斂:optimizer1 = tf.train.AdamOptimizer(learning_rate1).minimize(loss1)
任務B需要迭代10次收斂:optimizer2 = tf.train.AdamOptimizer(learning_rate2).minimize(loss2)
【當然這部分只是我的想法啦!沒什么科學依據】
參考資料:
什么是多任務學習
深度神經網絡中的多任務學習匯總
關于深度多任務學習的 3 點經驗
總結
- 上一篇: SiameseSentenceSimil
- 下一篇: Android官方开发文档Trainin