0
本文作者: skura | 2020-02-08 12:40 |
本文作者是 Omry Yadan,他是 Facebook 人工智能軟件工程師,創(chuàng)建了 Hydra。
Hydra 是最近發(fā)布的一個開源 Python 框架,由 Facebook AI 開發(fā),能夠簡化科研和其他復雜應用程序的開發(fā)。這個新框架功能強大,可以從命令行和配置文件中組合和重寫配置。作為 PyTorch 生態(tài)系統(tǒng)的一部分,Hydra 幫助 PyTorch 的研究人員和開發(fā)人員更容易地管理復雜的機器學習項目。Hydra 是通用的,可以應用于機器學習以外的領域。
這篇文章分為兩部分,第一部分描述開發(fā)機器學習軟件時出現的常見問題,第二部分主要是 Hydra 如何解決這些問題。
part1.你的代碼比你想象的更加復雜
命令行是每個軟件開發(fā)人員最先了解的知識之一。命令行的核心是一個字符串列表,這些字符串通常被分解為標志(例如,-verbose)和參數(例如,-port=80)。這對于許多簡單的應用程序來說已經足夠了,你可能只需要在命令行界面(CLI)解析庫中定義 2 到 3 個命令行參數就足夠了。
當人們開始使用你的應用程序時,他們將不可避免地發(fā)現缺少的功能。很快,你將添加更多功能,導致更多的命令行標志。這在機器學習中尤其常見。
上面的圖片來自 PyTorch ImageNet 訓練示例。盡管是一個很小的例子,但是命令行標志的數量已經很高了。其中一些標志在邏輯上描述了相同的組件,它們在理想情況下應該被分成一組(例如,與分布式訓練相關的標志),但是沒有一種簡單的方法可以將這些標志分組并使用。
在此示例的基礎上,你可能希望添加新功能,支持需要附加命令行標志的新模型、數據集或優(yōu)化器。你可以想象在這個例子,隨著你的擴展支持新的想法是如何做到的。
這種樣式的另一個微妙問題是,所有東西都需要解析的 args 對象。這會鼓勵耦合,并使單個組件更難在不同的項目中重用。
配置文件
一個常見的解決方案是切換到配置文件。配置文件可以是分層的,并且可以幫助減少定義命令行參數的代碼的復雜性。不幸的是,配置文件中也會面臨挑戰(zhàn),你將在下一節(jié)中看到。
配置文件很難更改
在嘗試時,你需要使用不同的配置選項運行應用程序。起初,你可能只是在每次運行之前更改配置文件,但你很快就會意識到跟蹤與每次運行相關聯的更改是非常困難的。
試圖解決該問題的方法可能是復制配置文件,在實驗后命名,并對新文件進行更改。這種方法也不是很完美,因為它創(chuàng)建了一個很長的配置文件進行跟蹤,這個文件將很快就不能與代碼同步,變得毫無用處。此外,通過查看實驗配置文件很難判斷你要做什么,因為它與其他配置文件 99% 相同。
最后,對于經常更改的內容,你可能會返回到命令行標志,以允許從命令行更改它們。這是乏味的,并且會讓命令行代碼再次變得復雜。理想情況下,你可以從命令行重寫配置中的所有內容,而不必為每種情況單獨編寫代碼。
配置文件變得單一
當開發(fā)人員編寫代碼時,他們喜歡將事情分解成很小的部分(模塊、函數)。這可以幫助他們保存代碼模型,并使代碼更易于維護。它還支持函數重用——調用一個函數比復制它容易。
配置文件不提供類似的功能。如果希望應用程序使用不同的配置選項,例如一個用于 ImageNet 數據集,一個用于 CIFAR-10 數據集,則有兩個選擇:
維護兩個配置文件
將這兩個選項放在一個配置文件中,并在運行時以某種方式使用所需的內容
第一種方法似乎很好,但后面你會意識到,隨著你增加更多的選項,事情很快就會崩潰。例如,除了兩個數據集選擇之外,你可能還想嘗試三種不同的模型體系結構(AlexNet、ResNet50 和一些新的、令人興奮的、你稱之為 BestNet 的東西)。你還可以在兩個損失函數之間進行選擇。這使組合總數達到 12 個!你確實希望避免維護 12 個類似的配置文件。
第二種方法最初的效果更好。你只需得到一個大的配置文件,該文件知道所選的兩個數據集、三個體系結構和兩個損失函數。但是,等等,當你在 AlexNet 和 ResNet50 上進行訓練時,你的學習速率需要有所不同,而且你需要在單個配置文件中表達出來。
這種復雜性也會泄漏到代碼中,現在需要找出在運行時使用的學習速率!在設計、運行和調試實驗時,大部分未使用的大型配置會產生顯著的認知負載。由于 90% 的配置未使用,很難判斷每次運行最重要 10% 在哪里。
通過添加從命令行重寫配置中所有內容的功能來組合配置,可以為這些問題提供一個強大的解決方案。由于這個原因,許多日益復雜的項目最終到達了開發(fā) Hydra 所提供的功能子集的必要位置。這種功能往往與單個項目的需求緊密結合,因此很難重用,迫使開發(fā)人員不斷地在每個新項目中重新發(fā)明輪子。
不幸的是,在許多開發(fā)人員意識到這一點的時候,他們已經有了一個復雜且不靈活的代碼庫,具有高耦合、硬編碼的配置。理想情況下,你希望像編寫代碼一樣編寫配置。這使你可以擴大項目的復雜性。
part2.像使用 Hydra 編寫代碼一樣編寫配置
如果你走到了這一步,你一定會想,對于我在第 1 部分中描述的那些軟件工程的問題,有什么神奇的解決方案?你可能會猜到它就是 Hydra。
Hydra 是 Facebook AI Research 開發(fā)的一個開源 Python 框架,它通過允許你組合傳遞給應用程序的配置來解決很多問題,包括第 1 部分中概述的問題。合成可以通過配置文件或命令行進行,合成配置中的所有內容也可以通過命令行重寫。
基本示例
下面示例的源代碼在這里可以找到:https://github.com/omry/hydra-article-code。
假設你的數據集的配置如下:
config.yaml
以下是加載此配置的簡單 Hydra 應用程序:
my_app.py
這里最有趣的一行是 @hydra.main()修飾器。它采用一個 config_ 路徑,提到了上面的 config.yaml 文件。
程序很好地打印了它得到的配置對象。毫無疑問,config 對象包含 ImageNet 數據集配置:
my_app 的常規(guī)輸出
我們現在可以從命令行重寫此配置文件中的任何內容:
重寫 dataset.path 時的輸出
構成示例
有時,你可能希望在兩個不同的數據集之間進行替換,每個數據集都有自己的配置。要支持此功能,請為數據集引入一個配置組,并在其中放置單個配置文件,每個選項一個:
你還可以在 config.yaml 中添加「defaults」部分,告訴 Hydra 如何編寫配置。在這種情況下,我們只想默認加載 cifar10 的配置,因為在它上面訓練更快:
config.yaml
這個應用看起來幾乎相同,唯一的區(qū)別是配置路徑現在指向 conf/config.yaml。運行應用程序時,會加載預期的 cifar10 配置:
但我們也可以很容易地選擇使用 imagenet:
你可以擁有多個配置組,讓我們在優(yōu)化器中添加一個:
默認情況下,還可以更新 config.yaml 以加載 adam:
config.yaml
運行應用程序時,我們會得到一個包含 cifar10 和 adam 的聯合配置:
這里還有很多可以談的,但現在,讓我們轉到下一個激動人心的特性。
Multirun
Multirun 是 Hydra 的一種功能,它可以多次運行你的函數,每次都組成一個不同的配置對象。這是一個自然的擴展,可以輕松地組合復雜的配置,并且非常方便地進行參數掃描,而無需編寫冗長的腳本。
例如,我們可以掃描所有 4 個組合(2 個數據集 X 2 個優(yōu)化器):
基本的內置啟動程序是串行運行,但是其他啟動程序插件可以并行運行代碼,甚至遠程運行代碼。這些插件還沒有公開,但在社區(qū)的幫助下,我希望很快能看到它們。
自動工作目錄
如果仔細觀察上面的輸出,你會注意到 sweep 輸出目錄是根據我運行命令的時間生成的。人們在做研究時經常遇到的一個問題是如何保存輸出。典型的解決方案是傳入一個指定輸出目錄的命令行標志,但這很快會變得乏味。當你希望同時運行多項任務,并且必須為每個任務傳遞不同的輸出目錄時,這尤其令人惱火。
Hydra 通過為每次運行生成輸出目錄并在運行代碼之前更改當前工作目錄來解決此問題。使用 --multirun 執(zhí)行掃描時,會為每個任務生成一個附加子目錄。
這樣可以很好地將來自同一 sweep 的任務分組在一起,同時保持每個任務與其他任務的輸出分離。
你仍然可以通過 Hydra 中的 API 訪問原始工作目錄。
original_cwd
從 /home/omry/dev/hydra 運行時的輸出:
生成的工作目錄可以完全自定義,這包括讓它作為路徑的一部分,包含命令行參數或配置中的任何其他內容。
寫在最后
本文中包含的只是 Hydra 提供的特性之一。其他功能包括動態(tài)選項卡完成、Python 日志記錄子系統(tǒng)的自動配置、庫和應用程序打包配置支持等等。
在 Facebook AI 中,我們使用 Hydra 從命令行直接向內部集群發(fā)送代碼。在社區(qū)的幫助下,我希望 Hydra 能夠成長為支持 AWS 和 GCP,并為 Facebook AI 之外的研究人員提供類似的功能。另一個感興趣的領域是命令行驅動的超參數優(yōu)化。第一個這樣的插件,Ax 正在開發(fā)中。
Hydra 是新的,我們剛剛開始了解它是如何改變事物的。
我期待著看到社區(qū)在未來幾年如何使用 Hydra。
要了解有關 Hydra 的更多信息,請參閱 Hydra 網站上的教程和文檔:https://hydra.cc/ 。
雷鋒網雷鋒網雷鋒網
雷峰網版權文章,未經授權禁止轉載。詳情見轉載須知。