本文將會(huì)介紹華為自研AI框架昇思MindSpore,這是一個(gè)面向全場景設(shè)計(jì)的AI計(jì)算框架,旨在為AI算法研究和生產(chǎn)部署提供一個(gè)統(tǒng)一、高效、安全的平臺(tái)。接下來,將詳細(xì)闡述MindSpore的定位、架構(gòu)、特性、以及其在端邊云全場景下的應(yīng)用和優(yōu)勢。
昇思MindSpore是面向“端-邊-云”全場景設(shè)計(jì)的AI框架,旨在彌合AI算法研究與生產(chǎn)部署之間的鴻溝。在算法研究階段,為開發(fā)者提供動(dòng)靜統(tǒng)一的編程體驗(yàn)以提升算法的開發(fā)效率;生產(chǎn)階段,自動(dòng)并行可以極大加快分布式訓(xùn)練的開發(fā)和調(diào)試效率,同時(shí)充分挖掘異構(gòu)硬件的算力;在部署階段,基于“端-邊-云”統(tǒng)一架構(gòu),應(yīng)對(duì)企業(yè)級(jí)部署和安全可信方面的挑戰(zhàn)。開源以來,秉持全場景協(xié)同、全流程極簡、全架構(gòu)統(tǒng)一三大價(jià)值主張,致力于增強(qiáng)開發(fā)易用性、提升原生支持大模型和AI+科學(xué)計(jì)算的體驗(yàn)。” 向上使能AI模型創(chuàng)新,對(duì)下兼容多樣性算力(NPU、GPU、CPU)。
昇思MindSpore整體架構(gòu)分為四層(如圖 1所示):
模型層,為開發(fā)者提供開箱即用的功能,該層主要包含預(yù)置的模型和開發(fā)套件,以及圖神經(jīng)網(wǎng)絡(luò)(GNN)、深度概率編程等熱點(diǎn)研究領(lǐng)域拓展庫;
表達(dá)層(MindExpression),為開發(fā)者提供AI模型開發(fā)、訓(xùn)練、推理的接口,支持開發(fā)者用原生Python語法開發(fā)和調(diào)試神經(jīng)網(wǎng)絡(luò),其特有的動(dòng)靜態(tài)圖統(tǒng)一能力使開發(fā)者可以兼顧開發(fā)效率和執(zhí)行性能,同時(shí)該層在生產(chǎn)和部署階段提供全場景統(tǒng)一的C++接口;
編譯優(yōu)化(MindCompiler),作為AI框架的核心,以全場景統(tǒng)一中間表達(dá)(MindIR)為媒介,將前端表達(dá)編譯成執(zhí)行效率更高的底層語言,同時(shí)進(jìn)行全局性能優(yōu)化,包括自動(dòng)微分、代數(shù)化簡等硬件無關(guān)優(yōu)化,以及圖算融合、算子生成等硬件相關(guān)優(yōu)化;
運(yùn)行時(shí),按照上層編譯優(yōu)化的結(jié)果對(duì)接并調(diào)用底層硬件算子,同時(shí)通過“端 - 邊 - 云”統(tǒng)一的運(yùn)行時(shí)架構(gòu), 支持包括聯(lián)邦學(xué)習(xí)在內(nèi)的“端 - 邊 - 云”AI 協(xié)同。
昇思MindSpore為開發(fā)者提供Python等語言的編程范式。借助基于源碼轉(zhuǎn)換,開發(fā)者可以使用原生Python控制語法和其他一些高級(jí)API,如元組(Tuple)、列表(List)和Lambda表達(dá)。
昇思MindSpore提供面向?qū)ο蠛兔嫦蚝瘮?shù)的編程范式。開發(fā)者可以基于nn.cell類派生定義所需功能的AI網(wǎng)絡(luò)或網(wǎng)絡(luò)的某一層(layer),并可通過對(duì)象的嵌套調(diào)用的方式將已定義的各種layer進(jìn)行組裝,完成整個(gè)AI網(wǎng)絡(luò)的定義。同時(shí)開發(fā)者也可以定義一個(gè)可被昇思MindSpore源到源編譯轉(zhuǎn)換的Python純函數(shù),通過昇思MindSpore提供的函數(shù)或裝飾器,將其加速執(zhí)行。
下面分別介紹昇思MindSpore支持的三類編程范式及其簡單示例。
面向?qū)ο缶幊蹋∣bject-oriented programming,OOP),是指一種將程序分解為封裝數(shù)據(jù)及相關(guān)操作的模塊(類)而進(jìn)行的編程方式,對(duì)象為類(class)的實(shí)例。面向?qū)ο缶幊虒?duì)象作為程序的基本單元,將程序和數(shù)據(jù)封裝其中,以提高軟件的重用性、靈活性和擴(kuò)展性,對(duì)象里的程序可以訪問及經(jīng)常修改對(duì)象相關(guān)聯(lián)的數(shù)據(jù)。
在一般的編程場景中,代碼(code)和數(shù)據(jù)(data)是兩個(gè)核心構(gòu)成部分。面向?qū)ο缶幊淌轻槍?duì)特定對(duì)象(Object)來設(shè)計(jì)數(shù)據(jù)結(jié)構(gòu),定義類(Class)。類通常由以下兩部分構(gòu)成,分別對(duì)應(yīng)了code和data:
- 方法(Methods)
- 屬性(Attributes)
對(duì)于同一個(gè)Class實(shí)例化(instantiation)后得到的不同對(duì)象而言,方法和屬性相同,不同的是屬性的值。不同的屬性值決定了對(duì)象的內(nèi)部狀態(tài),因此OOP能夠很好地進(jìn)行狀態(tài)管理。
下面為Python構(gòu)造簡單類的示例:
對(duì)于構(gòu)造神經(jīng)網(wǎng)絡(luò)來說,首要的組件就是網(wǎng)絡(luò)層(Layer),一個(gè)神經(jīng)網(wǎng)絡(luò)層包含以下部分:
- Tensor操作(Operation)
- 權(quán)重(Weights)
此二者恰好與類的Methods和Attributes一一對(duì)應(yīng),同時(shí)權(quán)重本身就是神經(jīng)網(wǎng)絡(luò)層的內(nèi)部狀態(tài),因此使用類來構(gòu)造Layer天然符合其定義。此外,我們在編程時(shí)希望使用神經(jīng)網(wǎng)絡(luò)層進(jìn)行堆疊,構(gòu)造神經(jīng)網(wǎng)絡(luò),使用OOP編程可以很容易地通過Layer對(duì)象組合構(gòu)造新的Layer類。
下面為使用昇思MindSpore構(gòu)造神經(jīng)網(wǎng)絡(luò)類的示例:
除神經(jīng)網(wǎng)絡(luò)層的構(gòu)造使用面向?qū)ο缶幊谭妒酵猓瑫N思MindSpore支持純面向?qū)ο缶幊谭绞綐?gòu)造神經(jīng)網(wǎng)絡(luò)訓(xùn)練邏輯,此時(shí)神經(jīng)網(wǎng)絡(luò)的正向計(jì)算、反向傳播、梯度優(yōu)化等操作均使用類進(jìn)行構(gòu)造。下面是純面向?qū)ο缶幊痰氖纠?/p>
此時(shí),不論是神經(jīng)網(wǎng)絡(luò)及其訓(xùn)練過程均使用繼承nn.Cell的類進(jìn)行管理,可以方便地作為計(jì)算圖進(jìn)行編譯加速。
函數(shù)式編程(Functional programming)是一種將計(jì)算機(jī)運(yùn)算視為函數(shù)運(yùn)算,并且避免使用程序狀態(tài)以及可變對(duì)象的編程范式。
在函數(shù)式編程中,函數(shù)被視為一等公民,這意味著它們可以綁定到名稱(包括本地標(biāo)識(shí)符),作為參數(shù)傳遞,并從其他函數(shù)返回,就像任何其他數(shù)據(jù)類型一樣。這允許以聲明性和可組合的風(fēng)格編寫程序,其中小功能以模塊化方式組合。
函數(shù)式編程有時(shí)被視為純函數(shù)式編程的同義詞,是將所有函數(shù)視為確定性數(shù)學(xué)函數(shù)或純函數(shù)的函數(shù)式編程的一個(gè)子集。當(dāng)使用一些給定參數(shù)調(diào)用純函數(shù)時(shí),它將始終返回相同的結(jié)果,并且不受任何可變狀態(tài)或其他副作用的影響。
函數(shù)式編程有兩個(gè)核心特點(diǎn),使其十分符合科學(xué)計(jì)算的需要:
- 編程函數(shù)語義與數(shù)學(xué)函數(shù)語義完全對(duì)等。
- 確定性,給定相同輸入必然返回相同輸出。無副作用。
由于確定性這一特點(diǎn),通過限制副作用,程序可以有更少的錯(cuò)誤,更容易調(diào)試和測試,更適合形式驗(yàn)證。下面是使用函數(shù)式編程的示例:
配合函數(shù)式編程范式的需要,昇思MindSpore提供了多種函數(shù)變換接口,涵蓋包括自動(dòng)微分、自動(dòng)向量化、自動(dòng)并行、即時(shí)編譯、數(shù)據(jù)下沉等功能模塊,下面簡單進(jìn)行介紹:
- 自動(dòng)微分:grad、value_and_grad,提供微分函數(shù)變換功能;
- 自動(dòng)向量化:vamp,用于沿參數(shù)軸映射函數(shù)fn的高階函數(shù);
- 自動(dòng)并行:shard,函數(shù)式算子切分,指定函數(shù)輸入/輸出Tensor的分布策略;
- 即時(shí)編譯:jit,將Python函數(shù)編譯為一張可調(diào)用的MindSpore圖;
- 數(shù)據(jù)下沉:data_sink,對(duì)輸入的函數(shù)進(jìn)行變換,獲得可使用數(shù)據(jù)下沉模式的函數(shù)。
基于上述函數(shù)變換接口,在使用函數(shù)式編程范式時(shí)可以快速高效地使用函數(shù)變換實(shí)現(xiàn)復(fù)雜的功能。
下面是函數(shù)式+面向?qū)ο笕诤暇幊痰牡湫瓦^程:
- 用類構(gòu)建神經(jīng)網(wǎng)絡(luò);
- 實(shí)例化神經(jīng)網(wǎng)絡(luò)對(duì)象;
- 構(gòu)造正向函數(shù),連接神經(jīng)網(wǎng)絡(luò)和損失函數(shù);
- 使用函數(shù)變換,獲得梯度計(jì)算(反向傳播)函數(shù);
- 構(gòu)造訓(xùn)練過程函數(shù);
- 調(diào)用函數(shù)進(jìn)行訓(xùn)練。
下面是函數(shù)式+面向?qū)ο笕诤暇幊痰暮唵问纠?/p>
如上述示例,在神經(jīng)網(wǎng)絡(luò)構(gòu)造時(shí),使用面向?qū)ο缶幊蹋窠?jīng)網(wǎng)絡(luò)層的構(gòu)造方式符合AI編程的習(xí)慣。在進(jìn)行前向計(jì)算和反向傳播時(shí),昇思MindSpore使用函數(shù)式編程,將前向計(jì)算構(gòu)造為函數(shù),然后通過函數(shù)變換,獲得grad_fn,最后通過執(zhí)行g(shù)rad_fn獲得權(quán)重對(duì)應(yīng)的梯度。
通過函數(shù)式+面向?qū)ο笕诤暇幊蹋缺WC了神經(jīng)網(wǎng)絡(luò)構(gòu)建的易用性,同時(shí)提高了前向計(jì)算和反向傳播等訓(xùn)練過程的靈活性,是昇思MindSpore推薦的默認(rèn)編程范式。
目前主流的AI框架有三種自動(dòng)微分技術(shù):
基于靜態(tài)計(jì)算圖的轉(zhuǎn)換:在編譯時(shí)將網(wǎng)絡(luò)轉(zhuǎn)換為靜態(tài)數(shù)據(jù)流圖,然后將鏈?zhǔn)揭?guī)則轉(zhuǎn)換為數(shù)據(jù)流圖,實(shí)現(xiàn)自動(dòng)微分。
基于動(dòng)態(tài)計(jì)算圖的轉(zhuǎn)換:以算子重載的方式記錄前向執(zhí)行時(shí)網(wǎng)絡(luò)的操作軌跡,然后將鏈?zhǔn)揭?guī)則應(yīng)用到動(dòng)態(tài)生成的數(shù)據(jù)流圖中,實(shí)現(xiàn)自動(dòng)微分。
基于源碼的轉(zhuǎn)換:該技術(shù)是從函數(shù)式編程框架演化而來,對(duì)中間表達(dá)(程序在編譯過程中的表達(dá)形式),以即時(shí)(Just-In-Time,JIT)編譯的形式進(jìn)行自動(dòng)微分變換,支持復(fù)雜的流程控制場景、高階函數(shù)和閉包。基于源碼轉(zhuǎn)化的自動(dòng)微分如圖所示。
昇思MindSpore開發(fā)了一種新的策略,即基于源碼轉(zhuǎn)換的自動(dòng)微分。一方面,它支持流程控制的自動(dòng)微分,因此構(gòu)建像PyTorch這樣的模型非常方便。另一方面,昇思MindSpore可以對(duì)神經(jīng)網(wǎng)絡(luò)進(jìn)行靜態(tài)編譯優(yōu)化,從而獲得良好的性能。
昇思MindSpore自動(dòng)微分的實(shí)現(xiàn)可以理解為對(duì)程序本身進(jìn)行符號(hào)微分,因?yàn)镸indSpore IR是函數(shù)式的中間表達(dá),它與基本代數(shù)中的復(fù)合函數(shù)有直觀的對(duì)應(yīng)關(guān)系,只要已知基礎(chǔ)函數(shù)的求導(dǎo)公式,就能推導(dǎo)出由任意基礎(chǔ)函數(shù)組成的復(fù)合函數(shù)的求導(dǎo)公式。MindSpore IR中每個(gè)原語操作可以對(duì)應(yīng)為基礎(chǔ)代數(shù)中的基礎(chǔ)函數(shù),這些基礎(chǔ)函數(shù)可以構(gòu)建更復(fù)雜的流程控制。
傳統(tǒng)AI框架主要有2種編程執(zhí)行形態(tài),靜態(tài)圖模式和動(dòng)態(tài)圖模式。靜態(tài)圖模式會(huì)基于開發(fā)者調(diào)用的框架接口,在編譯執(zhí)行時(shí)先生成神經(jīng)網(wǎng)絡(luò)的圖結(jié)構(gòu),然后再執(zhí)行圖中涉及的計(jì)算操作。靜態(tài)圖模式能有效感知神經(jīng)網(wǎng)絡(luò)各層算子間的關(guān)系情況,基于編譯技術(shù)進(jìn)行有效的編譯優(yōu)化以提升性能。
但傳統(tǒng)靜態(tài)圖需要開發(fā)者感知構(gòu)圖接口,組建或調(diào)試網(wǎng)絡(luò)比較復(fù)雜,且難于與常用Python庫、自定義Python函數(shù)進(jìn)行穿插使用。動(dòng)態(tài)圖模式,能有效解決靜態(tài)圖的編程較復(fù)雜問題,但由于程序按照代碼的編寫順序執(zhí)行,系統(tǒng)難于進(jìn)行整圖編譯優(yōu)化,導(dǎo)致相對(duì)性能優(yōu)化空間較少,特別面向DSA等專有硬件的優(yōu)化比較難于使能。
昇思MindSpore由于基于源碼轉(zhuǎn)換機(jī)制構(gòu)建神經(jīng)網(wǎng)絡(luò)的圖結(jié)構(gòu)。因此相比傳統(tǒng)的靜態(tài)圖模式,能有更易用的表達(dá)能力。同時(shí)也能更好的兼容動(dòng)態(tài)圖和靜態(tài)圖的編程接口,比如面向控制流,動(dòng)態(tài)圖可以直接基于Python的控制流關(guān)鍵字編程。而靜態(tài)圖需要基于特殊的控制流算子編程或者需要開發(fā)者編程指示控制流執(zhí)行分支。這導(dǎo)致了動(dòng)態(tài)圖和靜態(tài)圖編程差異大。
而昇思MindSpore的源碼轉(zhuǎn)換機(jī)制,可基于Python控制流關(guān)鍵字,直接使能靜態(tài)圖模式的執(zhí)行,使得動(dòng)靜態(tài)圖的編程統(tǒng)一性更高。同時(shí)開發(fā)者基于昇思MindSpore的接口,可以靈活的對(duì)Python代碼片段進(jìn)行動(dòng)靜態(tài)圖模式控制。即可以將程序局部函數(shù)以靜態(tài)圖模式執(zhí)行而同時(shí)其他函數(shù)按照動(dòng)態(tài)圖模式執(zhí)行。從而使得在與常用Python庫、自定義Python函數(shù)進(jìn)行穿插執(zhí)行使用時(shí),開發(fā)者可以靈活指定函數(shù)片段進(jìn)行靜態(tài)圖優(yōu)化加速,而不犧牲穿插執(zhí)行的編程易用性。
昇思MindSpore框架在靜態(tài)圖模式下,先將Python代碼編譯成靜態(tài)計(jì)算圖,然后執(zhí)行靜態(tài)計(jì)算圖。通過MindCompiler編譯器將Python代碼的AST表示轉(zhuǎn)換成ANF范式的MindIR表示,并基于MindIR表示展開編譯優(yōu)化和自動(dòng)微分處理。MindIR是一種基于圖表示的函數(shù)式IR,從函數(shù)式編程規(guī)定來看,它跟Python語言命令式編程是有所區(qū)別的,開發(fā)者編寫程序時(shí)需要遵循昇思MindSpore靜態(tài)圖語法支持,語法使用存在約束限制。
JIT Fallback是從靜態(tài)圖的角度出發(fā)考慮靜動(dòng)統(tǒng)一。通過JIT Fallback特性,靜態(tài)圖可以支持盡量多的動(dòng)態(tài)圖語法,使得靜態(tài)圖提供接近動(dòng)態(tài)圖的語法使用體驗(yàn),從而實(shí)現(xiàn)動(dòng)靜統(tǒng)一。JIT Fallback特性主要作用于MindCompiler編譯器,應(yīng)用于圖模式場景下的Python語法解析和支持,將純底層算子執(zhí)行的計(jì)算圖改造成,開發(fā)者的Python代碼和算子執(zhí)行交替混合執(zhí)行的計(jì)算圖。主要過程如下:
JIT Fallback特性主要作用于MindCompiler編譯器的實(shí)現(xiàn),應(yīng)用于圖模式場景下的Python語法解析和支持,將純底層算子執(zhí)行的計(jì)算圖改造成,開發(fā)者的Python代碼和算子執(zhí)行交替混合執(zhí)行的計(jì)算圖。主要過程包括:
檢測不支持語法。在圖編譯階段,識(shí)別檢測出圖模式不支持的Python語法。
生成解釋節(jié)點(diǎn)。針對(duì)不支持的Python語法,將相關(guān)語句保留下來,生成解釋節(jié)點(diǎn),并將解釋節(jié)點(diǎn)轉(zhuǎn)換為ANF IR表示。
推導(dǎo)和執(zhí)行解釋節(jié)點(diǎn)。解釋節(jié)點(diǎn)有兩種執(zhí)行方式:編譯時(shí)運(yùn)行和運(yùn)行時(shí)運(yùn)行。解釋節(jié)點(diǎn)是在編譯時(shí)進(jìn)行推導(dǎo)的,一般而言,解釋節(jié)點(diǎn)盡量在編譯時(shí)執(zhí)行,另一種方式則是在運(yùn)行時(shí)執(zhí)行。
在昇思MindSpore中,稱動(dòng)態(tài)圖模式為PyNative模式,因?yàn)榇a使用Python解釋器在該模式下運(yùn)行。在動(dòng)態(tài)圖模式下,框架按照Python執(zhí)行模型的所有算子,為每個(gè)算子生成計(jì)算圖,并將計(jì)算圖傳遞給后端進(jìn)行前向計(jì)算。在完成前向計(jì)算的同時(shí),根據(jù)前向算子所對(duì)應(yīng)的反向傳播源碼,轉(zhuǎn)換成單算子反向圖,最終在完成整體模型的前向計(jì)算后,生成模型對(duì)應(yīng)的完整反向圖,并傳遞給后端進(jìn)行執(zhí)行。
由于編譯器能獲得靜態(tài)圖的全局信息,所以靜態(tài)圖在大多數(shù)情況下都表現(xiàn)出更好的運(yùn)行性能。而動(dòng)態(tài)圖可以保證更好的易用性,使開發(fā)者能夠更加方便地構(gòu)建和修改模型。為了同時(shí)支持靜態(tài)圖和動(dòng)態(tài)圖,大多數(shù)先進(jìn)的訓(xùn)練框架需要維護(hù)兩種自動(dòng)微分機(jī)制,即基于Tape的自動(dòng)微分機(jī)制和基于圖的自動(dòng)微分機(jī)制。
昇思MindSpore是訓(xùn)推一體的AI框架,同時(shí)支持訓(xùn)練和推理等功能。同時(shí)昇思MindSpore支持CPU、GPU、NPU等多種芯片,并且在不同芯片上提供統(tǒng)一的編程使用接口以及可生成在多種硬件上加載執(zhí)行的離線模型。按照實(shí)際執(zhí)行環(huán)境和業(yè)務(wù)需求,提供多種規(guī)格的版本形態(tài),支持部署在云端、服務(wù)器端、手機(jī)等嵌入式設(shè)備端以及耳機(jī)等超輕量級(jí)設(shè)備端上的部署執(zhí)行。
輕量化推理是將訓(xùn)練好的模型部署到運(yùn)行環(huán)境中進(jìn)行推理的過程,模型部署的過程中需要解決訓(xùn)練模型到推理模型的轉(zhuǎn)換,硬件資源對(duì)模型的限制,模型推理的時(shí)延、功耗、內(nèi)存占用等指標(biāo)對(duì)整個(gè)系統(tǒng)的影響以及模型的安全等一系列的問題。
模型完成訓(xùn)練后,需要將模型及參數(shù)持久化成文件,不同的訓(xùn)練框架導(dǎo)出的模型文件中存儲(chǔ)的數(shù)據(jù)結(jié)構(gòu)不同,這給模型的推理系統(tǒng)帶來了不便。推理系統(tǒng)為了支持不同的訓(xùn)練框架的模型,需要將模型文件中的數(shù)據(jù)轉(zhuǎn)換成統(tǒng)一的數(shù)據(jù)結(jié)構(gòu)。此外,在訓(xùn)練模型轉(zhuǎn)換成推理模型的過程中,需要進(jìn)行一些如算子融合、常量折疊等模型的優(yōu)化以提升推理的性能。
推理模型部署到不同的場景,需要滿足不同的硬件設(shè)備的限制,例如,在具有強(qiáng)大算力的計(jì)算中心或數(shù)據(jù)中心的服務(wù)器上可以部署大規(guī)模的模型,而在邊緣側(cè)服務(wù)器、個(gè)人電腦以及智能手機(jī)上,力和內(nèi)存則相對(duì)有限,部署的模型的規(guī)模就相應(yīng)地要降低。在超低功耗的微控制器上,則只能部署非常簡單的機(jī)器學(xué)習(xí)模型。此外,不同硬件對(duì)于不同數(shù)據(jù)類型(如float32、float16、bfloat16、int8等)的支持程度也不相同。為了滿足這些硬件的限制,在有些場景下需要對(duì)訓(xùn)練好的模型進(jìn)行壓縮,降低模型的復(fù)雜度或者數(shù)據(jù)的精度,減少模型的參數(shù),以適應(yīng)硬件的限制。
模型部署到運(yùn)行環(huán)境中執(zhí)行推理,推理的時(shí)延、內(nèi)存占用、功耗等是影響開發(fā)者使用的關(guān)鍵因素,優(yōu)化模型推理的方式有兩種,一是設(shè)計(jì)專有的機(jī)器學(xué)習(xí)的芯片,相對(duì)于通用的計(jì)算芯片,這些專有芯片一般在能效比上具有很大的優(yōu)勢。二是通過軟硬協(xié)同最大程度地發(fā)揮硬件的能力。對(duì)于第二種方式,以CPU為例,如何切分?jǐn)?shù)據(jù)塊以滿足cache大小,如何對(duì)數(shù)據(jù)進(jìn)行重排以便計(jì)算時(shí)可以連續(xù)訪問,如何減少計(jì)算時(shí)的數(shù)據(jù)依賴以提升硬件流水線的并行,如何使用擴(kuò)展指令集以提升計(jì)算性能,這些都需要針對(duì)不同的CPU架構(gòu)進(jìn)行設(shè)計(jì)和優(yōu)化。
隨著 AI 的飛速發(fā)展,大規(guī)模和高質(zhì)量的數(shù)據(jù)對(duì)模型的效果和用戶的體驗(yàn)都變得越來越重要。與此同時(shí),數(shù)據(jù)的利用率成為了制約了 AI 的進(jìn)一步發(fā)展的瓶頸。隱私、監(jiān)管和工程等問題造成了設(shè)備與設(shè)備之間的數(shù)據(jù)不能共享,進(jìn)而導(dǎo)致了數(shù)據(jù)孤島問題的出現(xiàn)。為了解決這一難題,聯(lián)邦學(xué)習(xí)(Federated Learning,F(xiàn)L)應(yīng)運(yùn)而生。聯(lián)邦學(xué)習(xí)的概念最早在2016年被提了出來。在滿足用戶隱私保護(hù)、數(shù)據(jù)安全和政府法規(guī)的要求下,聯(lián)邦學(xué)習(xí)能有效地使用多方機(jī)構(gòu)的數(shù)據(jù)進(jìn)行機(jī)器學(xué)習(xí)建模。
MindSpore Federated是華為昇思MindSpore提出的一款開源聯(lián)邦學(xué)習(xí)框架,支持千萬級(jí)無狀態(tài)終端設(shè)備商用化部署,在用戶數(shù)據(jù)留存在本地的情況下,使能全場景智能應(yīng)用。MindSpore Federated專注于大規(guī)模參與方的橫向聯(lián)邦的應(yīng)用場景,使參與聯(lián)邦學(xué)習(xí)的各用戶在不共享本地?cái)?shù)據(jù)的前提下共建AI模型。MindSpore Federated主要解決隱私安全、大規(guī)模聯(lián)邦聚合、半監(jiān)督聯(lián)邦學(xué)習(xí)、通信壓縮和跨平臺(tái)部署等聯(lián)邦學(xué)習(xí)在工業(yè)場景部署的難點(diǎn)。
昇思MindSpore基于編譯技術(shù),提供了豐富的硬件無關(guān)優(yōu)化,如IR融合、代數(shù)化簡、常數(shù)折疊、公共子表達(dá)式消除等。同時(shí)昇思MindSpore針對(duì)NPU、GPU等不同硬件,也提供各種硬件優(yōu)化能力,從而更好的發(fā)揮硬件的大規(guī)模計(jì)算加速能力。
昇思MindSpore除了提供傳統(tǒng)AI框架常用優(yōu)化,還提供了一些比較有特色的技術(shù)。
昇思MindSpore等主流AI計(jì)算框架對(duì)開發(fā)者提供的算子通常是從開發(fā)者可理解、易使用角度進(jìn)行定義。每個(gè)算子承載的計(jì)算量不等,計(jì)算復(fù)雜度也各不相同。但從硬件執(zhí)行角度看,這種天然的、基于開發(fā)者角度的算子計(jì)算量劃分,并不高效,也無法充分發(fā)揮硬件資源計(jì)算能力。主要體現(xiàn)在:
計(jì)算量過大、過復(fù)雜的算子,通常很難生成切分較好的高性能算子,從而降低設(shè)備利用率;
計(jì)算量過小的算子,由于計(jì)算無法有效隱藏?cái)?shù)據(jù)搬移開銷,也可能會(huì)造成計(jì)算的空等時(shí)延,從而降低設(shè)備利用率;
硬件Device通常為多核、眾核結(jié)構(gòu),當(dāng)算子shape較小或其它原因引起計(jì)算并行度不夠時(shí),可能會(huì)造成部分核的空閑,從而降低設(shè)備利用率。特別是基于專用處理器架構(gòu)(Domain Specific Architecture,后文簡稱DSA)的芯片對(duì)這些因素更為敏感。如何最大化發(fā)揮硬件算力性能的同時(shí)使算子也能具備較好的易用性,一直以來是一個(gè)很大的挑戰(zhàn)。
在AI框架設(shè)計(jì)方面,目前業(yè)界主流采用圖層和算子層分層的實(shí)現(xiàn)方法。圖層負(fù)責(zé)對(duì)計(jì)算圖進(jìn)行融合或重組,算子層負(fù)責(zé)將融合或重組后的算子編譯為高性能的可執(zhí)行算子。
圖層通常采用基于Tensor的High-Level IR的處理和優(yōu)化,算子層則采用基于計(jì)算指令的Low-Level IR進(jìn)行分析和優(yōu)化。 這種人為分層處理顯著增加了圖、算兩層進(jìn)行協(xié)同優(yōu)化的難度。昇思MindSpore在過去幾年的技術(shù)實(shí)踐中,采用了圖算融合的技術(shù)來較好的解決了這個(gè)問題。
昇騰芯片上集成了AICORE、AICPU和CPU。其中,AICORE負(fù)責(zé)大型Tensor Vector運(yùn)算,AICPU負(fù)責(zé)標(biāo)量運(yùn)算,CPU負(fù)責(zé)邏輯控制和任務(wù)分發(fā)。
Host側(cè)CPU負(fù)責(zé)將圖或算子下發(fā)到昇騰芯片。昇騰芯片由于具備了運(yùn)算、邏輯控制和任務(wù)分發(fā)的功能,所以不需要與Host側(cè)的CPU進(jìn)行頻繁的交互,只需要將計(jì)算完的最終結(jié)果返回給Host側(cè),實(shí)現(xiàn)整圖下沉到Device執(zhí)行,避免Host-Device頻繁交互,減小了開銷。
為了充分使用昇騰芯片硬件功能,打造極致性能,昇思MindSpore提供了整圖下沉功能,目的是減少Host-Device交互開銷,有效的提升訓(xùn)練與推理的性能。
昇思MindSpore構(gòu)建的圖包含數(shù)據(jù)圖和計(jì)算圖,通過將數(shù)據(jù)圖下沉和計(jì)算圖下沉的方式,減少Host-Device交互開銷。且結(jié)合循環(huán)下沉可以實(shí)現(xiàn)多個(gè)Step下沉,進(jìn)一步減少Host和Device的交互次數(shù)。
梯度累積是一種將訓(xùn)練神經(jīng)網(wǎng)絡(luò)的數(shù)據(jù)樣本按Batch size拆分為幾個(gè)小Batch的方式,然后按順序進(jìn)行計(jì)算。
神經(jīng)網(wǎng)絡(luò)模型由許多相互連接的神經(jīng)網(wǎng)絡(luò)單元所組成,在所有神經(jīng)網(wǎng)絡(luò)層中,樣本數(shù)據(jù)會(huì)不斷向前傳播。在通過所有層后,網(wǎng)絡(luò)模型會(huì)輸出樣本的預(yù)測值,通過損失函數(shù)然后計(jì)算每個(gè)樣本的損失值(誤差)。神經(jīng)網(wǎng)絡(luò)通過反向傳播,去計(jì)算損失值相對(duì)于模型參數(shù)的梯度。最后這些梯度信息用于對(duì)網(wǎng)絡(luò)模型中的參數(shù)進(jìn)行更新。
梯度累積只計(jì)算神經(jīng)網(wǎng)絡(luò)模型,并不及時(shí)更新網(wǎng)絡(luò)模型的參數(shù),同時(shí)在計(jì)算的時(shí)候累積得到的梯度信息,最后統(tǒng)一使用累積的梯度來對(duì)參數(shù)進(jìn)行更新。
$$ ext{accumulated} = sum_{i=0}^{N} ext{grad}_i\ $$
在不更新模型變量的時(shí)候,實(shí)際上是把原來的數(shù)據(jù)Batch size分成幾個(gè)小的Mini-Batch,每個(gè)step中使用的樣本實(shí)際上是更小的數(shù)據(jù)集。
在N個(gè)step內(nèi)不更新變量,使所有Mini-Batch使用相同的模型變量來計(jì)算梯度,以確保計(jì)算出來得到相同的梯度和權(quán)重信息,算法上等價(jià)于使用原來沒有切分的Batch size大小一樣。即:
$$ heta_i = heta_{i-1} - ext{lr} sum_{i=0}^{N} ext{grad}_i\ $$
最終在上面步驟中累積梯度會(huì)產(chǎn)生與使用全局Batch size大小相同的梯度總和。
與傳統(tǒng)的分布式訓(xùn)練中的梯度更新不同,自適應(yīng)梯度求和考慮到梯度的方向。在網(wǎng)絡(luò)訓(xùn)練初期,不同batch獲得的梯度更新方向基本是平行的,但是隨著訓(xùn)練進(jìn)行,梯度更新方向趨向于正交。而且網(wǎng)絡(luò)的不同層梯度更新的正交性差異也是比較大的。
以兩個(gè)訓(xùn)練節(jié)點(diǎn)為例,梯度的更新原理如下:
$$ begin{aligned} w' &= w_0 - alpha left[ left( 1 - frac{(g_2^T cdot g_1)}{2 cdot | g_1 |^2} ight) g_1 + left( 1 - frac{(g_2^T cdot g_1)}{2 cdot | g_2 |^2} ight) g_2 ight] \ &= w_0 - alpha cdot ext{Adasum}(g_1, g_2) end{aligned}\ $$
其中,g1是訓(xùn)練節(jié)點(diǎn)1的梯度,g2是訓(xùn)練節(jié)點(diǎn)2的梯度。當(dāng)訓(xùn)練節(jié)點(diǎn)拓展到n(n=2x,x=1,2,3?)個(gè)時(shí),采用遞歸的方式來對(duì)問題進(jìn)行分解,遞歸公式如下:
$$ begin{aligned} ext{Adasum}(g_{[0,n]}) &= ext{Adasum}left( ext{Adasum}(g_{[0,n/2]}), ext{Adasum}(g_{[n/2,n]}) ight) end{aligned}\ $$
從上述公式中可見,論文中是對(duì)梯度更新,考慮到優(yōu)化器(optimizer)對(duì)梯度的操作不一定滿足線性轉(zhuǎn)換,因此優(yōu)化為對(duì)經(jīng)過optimizer后的網(wǎng)絡(luò)權(quán)重差值(delta weights)做adasum操作。
另外,在實(shí)際應(yīng)用過程中,為了優(yōu)化通信開銷,通常會(huì)采取Adasum和傳統(tǒng)Reducesum混合的執(zhí)行方式,如下圖所示:
如果您想了解更多AI知識(shí),與AI專業(yè)人士交流,請立即訪問昇騰社區(qū)官方網(wǎng)站https://www.hiascend.com/或者深入研讀《AI系統(tǒng):原理與架構(gòu)》一書,這里匯聚了海量的AI學(xué)習(xí)資源和實(shí)踐課程,為您的AI技術(shù)成長提供強(qiáng)勁動(dòng)力。不僅如此,您還有機(jī)會(huì)投身于全國昇騰AI創(chuàng)新大賽和昇騰AI開發(fā)者創(chuàng)享日等盛事,發(fā)現(xiàn)AI世界的無限奧秘~