GPT大語(yǔ)言模型Alpaca-lora本地化部署實(shí)踐
模型介紹
Alpaca模型是斯坦福大學(xué)研發(fā)的LLM(Large Language Model,大語(yǔ)言)開源模型,是一個(gè)在52K指令上從LLaMA 7B(Meta公司開源的7B)模型微調(diào)而來(lái),具有70億的模型參數(shù)(模型參數(shù)越大,模型的推理能力越強(qiáng),當(dāng)然隨之訓(xùn)練模型的成本也就越高)。
LoRA,英文全稱Low-Rank Adaptation of Large Language Models,直譯為大語(yǔ)言模型的低階適應(yīng),這是微軟的研究人員為了解決大語(yǔ)言模型微調(diào)而開發(fā)的一項(xiàng)技術(shù)。如果想讓一個(gè)預(yù)訓(xùn)練大語(yǔ)言模型能夠執(zhí)行特定領(lǐng)域內(nèi)的任務(wù),一般需要做fine-tuning,但是目前推理效果好的大語(yǔ)言模型參數(shù)維度非常非常大,有些甚至是上千億維,如果直接在大語(yǔ)言模型上做fine-tuning,計(jì)算量會(huì)非常的大,成本也會(huì)非常的高。
’LoRA的做法是凍結(jié)預(yù)訓(xùn)練好的模型參數(shù),然后在每個(gè)Transformer塊里注入可訓(xùn)練的層,由于不需要對(duì)模型的參數(shù)重新計(jì)算梯度,所以,會(huì)大大的減少計(jì)算量。
具體如下圖所示,核心思想是在原始預(yù)訓(xùn)練模型增加一個(gè)旁路,做一個(gè)降維再升維的操作。訓(xùn)練的時(shí)候固定預(yù)訓(xùn)練模型的參數(shù),只訓(xùn)練降維矩陣 A 與升維矩陣 B。而模型的輸入輸出維度不變,輸出時(shí)將 BA 與預(yù)訓(xùn)練語(yǔ)言模型的參數(shù)疊加。
用隨機(jī)高斯分布初始化 A,用 0 矩陣初始化 B。這樣能保證訓(xùn)練時(shí),新增的旁路BA=0,從而對(duì)模型結(jié)果沒(méi)有影響。在推理時(shí),將左右兩部分的結(jié)果加到一起,即h=Wx+BAx=(W+BA)x,所以,只要將訓(xùn)練完成的矩陣乘積BA跟原本的權(quán)重矩陣W加到一起作為新權(quán)重參數(shù)替換原始預(yù)訓(xùn)練語(yǔ)言模型的W即可,不會(huì)增加額外的計(jì)算資源。LoRA 的最大優(yōu)勢(shì)是訓(xùn)練速度更快,使用的內(nèi)存更少。
本文進(jìn)行本地化部署實(shí)踐的Alpaca-lora模型就是Alpaca模型的低階適配版本。本文將對(duì)Alpaca-lora模型本地化部署、微調(diào)和推理過(guò)程進(jìn)行實(shí)踐并描述相關(guān)步驟。
GPU服務(wù)器環(huán)境部署
本文進(jìn)行部署的GPU服務(wù)器具有4塊獨(dú)立的GPU,型號(hào)是P40,單個(gè)P40算力相當(dāng)于60個(gè)同等主頻CPU的算力。
如果只是測(cè)試覺(jué)得物理卡太貴了,也可以使用“平替版”——GPU云服務(wù)器。相比于物理卡,用GPU云服務(wù)器搭建不僅能保障彈性的高性能計(jì)算,還有這些好處——
- 高性價(jià)比:按時(shí)計(jì)費(fèi),一小時(shí)才十幾元,可以隨時(shí)根據(jù)自己的需求調(diào)配;靈活資源管理、可擴(kuò)展性、彈性伸縮等云計(jì)算優(yōu)勢(shì),根據(jù)業(yè)務(wù)或個(gè)人訓(xùn)練的需要,快速調(diào)整計(jì)算資源,滿足模型的訓(xùn)練和部署需求;
- 開放性:云計(jì)算的開放性讓用戶更容易進(jìn)行資源的共享和協(xié)作,為AI模型的研究和應(yīng)用提供了更廣泛的合作機(jī)會(huì);
- 豐富的API和SDK:云計(jì)算廠商提供了豐富的API和SDK,使得用戶能夠輕松地接入云平臺(tái)的各種服務(wù)和功能,進(jìn)行定制化開發(fā)和集成。
京東云的GPU云主機(jī)最近在做618活動(dòng),非常劃算
https://www.jdcloud.com/cn/calculator/calHost
拿到GPU服務(wù)器我們首先就是安裝顯卡驅(qū)動(dòng)和CUDA驅(qū)動(dòng)(是顯卡廠商N(yùn)VIDIA推出的運(yùn)算平臺(tái)。 CUDA是一種由NVIDIA推出的通用并行計(jì)算架構(gòu),該架構(gòu)使GPU能夠解決復(fù)雜的計(jì)算問(wèn)題)。
顯卡驅(qū)動(dòng)需要到NVIDIA的官方網(wǎng)站去查找相應(yīng)的顯卡型號(hào)和適配的CUDA版本,下載地址:
https://www.nvidia.com/Download/index.aspx ,選擇相應(yīng)的顯卡和CUDA版本就可以下載驅(qū)動(dòng)文件啦。
我下載的文件是NVIDIA-Linux-x86_64-515.105.01.run,這是一個(gè)可執(zhí)行文件,用root權(quán)限執(zhí)行即可,注意安裝驅(qū)動(dòng)過(guò)程中不能有運(yùn)行的nvidia進(jìn)程,如果有需要全部kill掉,否則會(huì)安裝失敗,如下圖所示:
然后一路next,沒(méi)有報(bào)錯(cuò)的話就安裝成功啦。為了后續(xù)查看顯卡資源情況,最好還是再安裝一個(gè)顯卡監(jiān)控工具,比如nvitop,用pip install nvitop即可,這里注意,由于不同服務(wù)器python版本有差異,最好安裝anaconda部署自己的私有python空間,防止運(yùn)行時(shí)報(bào)各種奇怪的錯(cuò)誤,具體步驟如下:
1.安裝anaconda 下載方式:wget
https://repo.anaconda.com/archive/Anaconda3-5.3.0-Linux-x86_64.sh。 安裝命令: sh Anaconda3-5.3.0-Linux-x86_64.sh 每個(gè)安裝步驟都輸入“yes”,最后conda init后完成安裝,這樣每次進(jìn)入安裝用戶的session,都會(huì)直接進(jìn)入自己的python環(huán)境。如果安裝最后一步選擇no,即不進(jìn)行conda init,則后續(xù)可以通過(guò)source /home/jd_ad_sfxn/anaconda3/bin/activate來(lái)進(jìn)入到私有的python環(huán)境。
2.安裝setuptools 接下來(lái)需要安裝打包和分發(fā)工具setuptools,下載地址:wget
https://files.pythonhosted.org/packages/26/e5/9897eee1100b166a61f91b68528cb692e8887300d9cbdaa1a349f6304b79/setuptools-40.5.0.zip 安裝命令: unzip setuptools-40.5.0.zip cd setuptools-40.5.0/ python setup.py install
3.安裝pip 下載地址:wget
https://files.pythonhosted.org/packages/45/ae/8a0ad77defb7cc903f09e551d88b443304a9bd6e6f124e75c0fbbf6de8f7/pip-18.1.tar.gz 安裝命令: tar -xzf pip-18.1.tar.gz cd pip-18.1 python setup.py install
至此,漫長(zhǎng)的安裝過(guò)程終于告一段落了,我們現(xiàn)在創(chuàng)建一個(gè)私有的python空間,執(zhí)行:
conda create -n alpaca pythnotallow=3.9
conda activate alpaca
然后驗(yàn)證一下,如下圖所示說(shuō)明已經(jīng)創(chuàng)建成功啦。
模型訓(xùn)練
上文已經(jīng)把GPU服務(wù)器的基礎(chǔ)環(huán)境安裝好了,下面我們就要開始激動(dòng)人心的模型訓(xùn)練了(激動(dòng)ing),在訓(xùn)練之前我們首先需要下載模型文件,下載地址:
https://github.com/tloen/alpaca-lora ,整個(gè)模型都是開源的,真好!首先把模型文件下載到本地,執(zhí)行g(shù)it clone https://github.com/tloen/alpaca-lora.git .。
本地會(huì)有文件夾alpaca-lora,然后cd alpaca-lora到文件夾內(nèi)部執(zhí)行
pip install -r requirements.txt
這個(gè)過(guò)程可能會(huì)比較慢,需要從網(wǎng)上下載大量的依賴包,過(guò)程中可能也會(huì)報(bào)各種包沖突,依賴沒(méi)有等問(wèn)題,這塊只能見招拆招,缺什么裝什么(解決包依賴和版本沖突確實(shí)是個(gè)頭疼的事情,不過(guò)這步做不好,模型也跑不起來(lái),所以只能耐心的一點(diǎn)一點(diǎn)解決),這里痛苦的過(guò)程就不贅述了,因?yàn)椴煌瑱C(jī)器可能遇到的問(wèn)題也不太一樣,參考意義不是很大。
如果安裝過(guò)程執(zhí)行完成,并沒(méi)再有報(bào)錯(cuò)信息,并提示Successful compeleted,那么恭喜你啦,萬(wàn)里長(zhǎng)征已經(jīng)走完一半啦,你已經(jīng)離成功很近了,再堅(jiān)持一下下就很有可能成功啦:)。
由于我們的目標(biāo)是對(duì)模型進(jìn)行fine-tuning,所以我們得有一個(gè)fine-tuning的目標(biāo),由于原始模型對(duì)中文支持并不好,所以我們的目標(biāo)就有了,用中文語(yǔ)料庫(kù)讓模型更好的支持中文,這個(gè)社區(qū)也給我準(zhǔn)備好了,我們直接下載中文的語(yǔ)料庫(kù)就好了,在本地執(zhí)行 wget
https://github.com/LC1332/Chinese-alpaca-lora/blob/main/data/trans_chinese_alpaca_data.json?raw=true ,將后面模型訓(xùn)練用到的語(yǔ)料庫(kù)下載到alpaca-lora根目錄下(后面方便使用)。
語(yǔ)料庫(kù)的內(nèi)容就是很多的三元組(instruction,input,output,如下圖所示),instruction就是指令,讓模型做什么事,input就是輸入,output是模型的輸出,根據(jù)指令和輸入,訓(xùn)練模型應(yīng)該輸出什么信息,讓模型能夠更好的適應(yīng)中文。
好的,到現(xiàn)在為止,萬(wàn)里長(zhǎng)征已經(jīng)走完2/3了,別著急訓(xùn)練模型,我們現(xiàn)在驗(yàn)證一下GPU環(huán)境和CUDA版本信息,還記得之前我們安裝的nvitop嘛,現(xiàn)在就用上了,在本地直接執(zhí)行nvitop,我們就可以看到GPU環(huán)境和CUDA版本信息了,如下圖:
在這里我們能夠看到有幾塊顯卡,驅(qū)動(dòng)版本和CUDA版本等信息,當(dāng)然最重要的我們還能看到GPU資源的實(shí)時(shí)使用情況。
怎么還沒(méi)到模型訓(xùn)練呢,別著急呀,這就來(lái)啦。
我們先到根目錄下然后執(zhí)行訓(xùn)練模型命令:
如果是單個(gè)GPU,那么執(zhí)行命令即可:
python finetune.py \
--base_model 'decapoda-research/llama-7b-hf' \
--data_path 'trans_chinese_alpaca_data.json' \
--output_dir './lora-alpaca-zh'
如果是多個(gè)GPU,則執(zhí)行:
WORLD_SIZE=2 CUDA_VISIBLE_DEVICES=0,1 torchrun \
--nproc_per_node=2 \
--master_port=1234 \
finetune.py \
--base_model 'decapoda-research/llama-7b-hf' \
--data_path 'trans_chinese_alpaca_data.json' \
--output_dir './lora-alpaca-zh'
如果可以看到進(jìn)度條在走,說(shuō)明模型已經(jīng)啟動(dòng)成功啦。
在模型訓(xùn)練過(guò)程中,每迭代一定數(shù)量的數(shù)據(jù)就會(huì)打印相關(guān)的信息,會(huì)輸出損失率,學(xué)習(xí)率和代信息,如上圖所示,當(dāng)loss波動(dòng)較小時(shí),模型就會(huì)收斂,最終訓(xùn)練完成。
我用的是2塊GPU顯卡進(jìn)行訓(xùn)練,總共訓(xùn)練了1904分鐘,也就是31.73個(gè)小時(shí),模型就收斂了,模型訓(xùn)練是個(gè)漫長(zhǎng)的過(guò)程,所以在訓(xùn)練的時(shí)候我們可以適當(dāng)?shù)姆潘梢幌?,做點(diǎn)其他的事情:)。
模型推理
模型訓(xùn)練好后,我們就可以測(cè)試一下模型的訓(xùn)練效果了,由于我們是多個(gè)GPU顯卡,所以想把模型參數(shù)加載到多個(gè)GPU上,這樣會(huì)使模型推理的更快,需要修改
generate.py 文件,添加下面這樣即可。
然后我們把服務(wù)啟起來(lái),看看效果,根目錄執(zhí)行:
python generate.py --base_model "decapoda-research/llama-7b-hf" \
--lora_weights './lora-alpaca-zh' \
--load_8bit
其中./lora-alpaca-zh目錄下的文件,就是我們剛剛fine tuning模型訓(xùn)練的參數(shù)所在位置,啟動(dòng)服務(wù)的時(shí)候把它加載到內(nèi)存(這個(gè)內(nèi)存指的是GPU內(nèi)存)里面。
如果成功,那么最終會(huì)輸出相應(yīng)的IP和Port信息,如下圖所示:
我們可以用瀏覽器訪問(wèn)一下看看,如果能看到頁(yè)面,就說(shuō)明服務(wù)已經(jīng)啟動(dòng)成功啦。
激動(dòng)ing,費(fèi)了九牛二虎之力,終于成功啦??!
因?yàn)槲覀兡繕?biāo)是讓模型說(shuō)中文,所以我們測(cè)試一下對(duì)中文的理解,看看效果怎么樣?
簡(jiǎn)單的問(wèn)題,還是能給出答案的,但是針對(duì)稍微復(fù)雜一點(diǎn)的問(wèn)題,雖然能夠理解中文,但是并沒(méi)有用中文進(jìn)行回答,訓(xùn)練后的模型還是不太穩(wěn)定啊。
在推理的時(shí)候我們也可以監(jiān)控一下GPU的變化,可以看到GPU負(fù)載是比較高的,說(shuō)明GPU在進(jìn)行大量的計(jì)算來(lái)完成推理。
總結(jié)
1.效果問(wèn)題:由于語(yǔ)料庫(kù)不夠豐富,所以目前用社區(qū)提供的語(yǔ)料庫(kù)訓(xùn)練的效果并不是很好,對(duì)中文的理解力有限,如果想訓(xùn)練出能夠執(zhí)行特定領(lǐng)域的任務(wù),則需要大量的語(yǔ)料支持,同時(shí)訓(xùn)練時(shí)間也會(huì)更長(zhǎng);
2. 推理時(shí)間問(wèn)題:由于目前部署的GPU服務(wù)器有4塊GPU,能夠執(zhí)行的有3塊,基于3塊GPU,在推理的時(shí)候還是比較吃力的,執(zhí)行一次交互需要大概30s-1min,如果達(dá)到chatGPT那樣實(shí)時(shí)返回,則需要大量的算力進(jìn)行支持,可以反推,chatGPT后臺(tái)肯定是有大集群算力支持的,所以如果想做成服務(wù),成本投入是需要考量的一個(gè)問(wèn)題;
3. 中文亂碼問(wèn)題:在input為中文的時(shí)候,有時(shí)候返回結(jié)果會(huì)亂碼,懷疑跟切詞有關(guān),由于中文的編碼問(wèn)題,中文不像英文以空格區(qū)分,所以可能會(huì)有一定的亂碼情況產(chǎn)生,調(diào)用open AI 的API也會(huì)有這種情況,后面看看社區(qū)是否有相應(yīng)解決辦法;
4. 模型選擇問(wèn)題:由于目前GPT社區(qū)比較活躍,模型的產(chǎn)生和變化也是日新月異,由于時(shí)間倉(cāng)促,目前只調(diào)研了alpaca-lora模型的本地化部署,后面針對(duì)實(shí)際落地的應(yīng)用應(yīng)該也會(huì)有更好的更低成本的落地方案,需要持續(xù)跟進(jìn)社區(qū)的發(fā)展,選擇合適的開源方案。
京東云P40型號(hào)GPU的【ChatGLM語(yǔ)言模型】實(shí)踐篇詳見:https://www.toutiao.com/article/7226282048003375675/
作者:京東零售 駱永健
內(nèi)容來(lái)源:京東云開發(fā)者社區(qū)