一、從 LLaMA 到 Alpaca:大模型的小訓練
1.1 LLaMA 概要與實踐
LLaMA(Large Language Model Meta AI) 是由 Meta AI 發布了一款全新的大型語言模型,共有7B、13B、33B、65B 四種版本,其模型參數如下表所示:
與原始的 transformer Decoder 相比,LLaMA主要有以下改進:
預歸一化(Pre-normalization)[GPT3]
為了提高訓練的穩定性,LLaMA對每個transformer子層的輸入進行歸一化,而不是對輸出進行歸一化。同時使用RMSNorm歸一化函數。
SwiGLU激活函數[PaLM]
LLaMA用SwiGLU激活函數取代ReLU非線性,以提高性能。SwiGLU激活函數的實現如下:
其中 ,,具體實現參考這里[1]。
旋轉嵌入(Rotary pos)[GPTNeo]
LLaMA刪除了絕對位置嵌入,取而代之的是在網絡的每一層添加旋轉位置嵌入(RoPE),RoPE的實現參見這里[2]。當前 HuggingFace 已經實現了 LLaMA 模型 代碼,可通過以下方式直接調用:
from?transformers?import?LlamaForCausalLM USE_8BIT?=?True?#?use?8-bit?quantization;?otherwise,?use?fp16 model?=?LlamaForCausalLM.from_pretrained( ????????????"pretrained/path", ????????????load_in_8bit=USE_8BIT, ????????????torch_dtype=torch.float16, ????????????device_map="auto", ????????) if?not?USE_8BIT: ????model.half()??#?use?fp16 model.eval()
1.2 Alpaca 如何使用小成本訓練大模型
如下圖所示,Stanford的研究者使用 52K 個 intruction-following examples 來微調 LLaMA 7B 模型,從而生成了 Alpaca[3] 7B。
Alpaca 團隊使用 self-instruct[4] 提供的 175 個 prompts,調用 OpenAI 的text-davinci-003模型,利用 OpenAI 的模型來產生有價值的 instructions 。
將 OpenAI 性能完備的模型作為 Teacher,來指導參數更少的 Alpaca 模型進行訓練,大幅降低了訓練成本 。其中調用 OpenAI API 的成本不到 500 美元,另外微調 7B 參數的 LLaMA 模型,使用云服務商提供的 8 塊 80GB A100 顯卡,訓練 3 小時,消費不到 100 美元,因此整體成本是小于 600 美元。
二、Alpaca 的優化、訓練及應用
2.1 alpaca-lora 的優化
alpace-lora[5] 是在alpaca的基礎上把訓練方式改成用lora訓練,僅需要在消費級的GPU上經過數小時的訓練,就可以達到和alpaca差不多的效果。
LoRA(Low-Rank Adaptation) 技術
LoRA 的思想很簡單,即在原始 Pretrained Weights 旁邊增加一個旁路,做一個降維再升維的操作,來模擬所謂的 intrinsic rank 。訓練的時候固定 Pretrained Weights 的參數,只訓練降維矩陣 與升維矩陣 。而模型的輸入輸出維度不變,輸出時將 與 Pretrained Weights 的參數疊加。用隨機高斯分布初始化 ,用0矩陣初始化 ,保證訓練的開始此旁路矩陣依然是 0 矩陣。
具體來看,假設預訓練的矩陣為,它的更新可表示為:
其中秩。
LoRA與Transformer的結合也很簡單,僅在QKV attention的計算中增加一個旁路,而不動MLP模塊。基于大模型的內在低秩特性,增加旁路矩陣來模擬全模型參數微調,LoRA通過簡單有效的方案來達成輕量微調的目的,可以將現在的各種大模型通過輕量微調變成各個不同領域的專業模型。
2.2 PEFT(Parameter-Efficient Fine-Tuning) 方法
隨著模型變得越來越大,在消費級硬件上對模型進行全部參數的微調變得不可行。此外,為每個下游任務獨立存儲和部署微調模型變得非常昂貴,因為微調模型與原始預訓練模型的大小相同。PEFT 方法旨在解決這兩個問題,PEFT 方法僅微調少量 (額外) 模型參數,同時凍結預訓練 LLM 的大部分參數,從而大大降低了計算和存儲成本。
HuggingFace 開源的一個高效微調大模型的 PEFT 庫,目前包含LoRA,Prefix Tuning,Prompt Tuning,P-Tuning 四種算法,下面簡要介紹后三種:
Prefix Tuning
Prefix Tuning 算法是根據 下游任務 "前綴指令文本" 的所有層的embeding表示,學習到的前綴指令文本向量可以挖掘大模型的潛力去引導模型完成特定任務。
P-Tuning
P-Tuning 算法和 Prefix Tuning 的想法很相似,想通過微調"指令文本",讓指令文本去挖掘大模型的潛力去完成特定的任務。但是 P-Tuning 只學習 "指令文本" 輸入層embeding的的表示。為了增強 "指令文本"的連續性,采用了一個 MLP(LSTM) 的結果去encoding "指令文本"。從微調參數量來看只有 0.65% 比 Prefix Tuning 和 LoRA 這些在所有層都增加參數的方法要少。
Prompt Tuning
Prompt Tuning 算法和 P-Tuning 很像,且更簡單,就是是根據 下游任務 "指令文本" 輸入層embeding的的表示。Prompt Tuning 沒有增加任何的層,直接使用微調指令文本(prompt) 的embeding向量。
2.3 使用 PEFT 訓練 alpaca-lora
以下僅說明過程,完整代碼見這里[6]。
step 1. 模塊的加載及初始化
import?torch import?transformers from?datasets?import?load_dataset from?peft?import?LoraConfig,?get_peft_model,?get_peft_model_state_dict,?prepare_model_for_int8_training,?set_peft_model_state_dict, from?transformers?import?LlamaForCausalLM,?LlamaTokenizer? model?=?LlamaForCausalLM.from_pretrained(base_model,?load_in_8bit=True,?torch_dtype=torch.float16,?device_map=device_map,) tokenizer?=?LlamaTokenizer.from_pretrained(base_model) model?=?prepare_model_for_int8_training(model) config?=?LoraConfig( ????r=lora_r, ????lora_alpha=lora_alpha, ????target_modules=lora_target_modules, ????lora_dropout=lora_dropout, ????bias="none", ????task_type="CAUSAL_LM", ) model?=?get_peft_model(model,?config)
step 2. 準備data 和 trainer 并進行訓練
data?=?load_dataset(data_path) trainer?=?transformers.Trainer( ????model=model, ????train_dataset=train_data, ????eval_dataset=val_data, ????args=transformers.TrainingArguments( ????????per_device_train_batch_size=micro_batch_size, ????????gradient_accumulation_steps=gradient_accumulation_steps, ????????warmup_steps=100, ????????num_train_epochs=num_epochs, ????????learning_rate=learning_rate, ????????fp16=True, ????????logging_steps=10, ????????optim="adamw_torch", ????????evaluation_strategy="steps"?if?val_set_size?>?0?else?"no", ????????save_strategy="steps", ????????eval_steps=200?if?val_set_size?>?0?else?None, ????????save_steps=200, ????????output_dir=output_dir, ????????save_total_limit=3, ????????load_best_model_at_end=True?if?val_set_size?>?0?else?False, ????????ddp_find_unused_parameters=False?if?ddp?else?None, ????????group_by_length=group_by_length, ????????report_to="wandb"?if?use_wandb?else?None, ????????run_name=wandb_run_name?if?use_wandb?else?None, ????), ????data_collator=transformers.DataCollatorForSeq2Seq( ????????tokenizer,?pad_to_multiple_of=8,?return_tensors="pt",?padding=True ????), ) trainer.train(resume_from_checkpoint=resume_from_checkpoint)
2.4 更多類似模型
Baize (白澤)
論文:https://arxiv.org/pdf/2304.01196.pdf
demo: Baize Lora 7B - a Hugging Face Space by project-baize
repo: https://github.com/project-baize/baize
Luotuo (駱駝,Chinese)
repo: https://github.com/LC1332/Luotuo-Chinese-LLM
Koala (考拉)
blog: Koala: A Dialogue Model for Academic Research
demo: FastChat
repo: https://github.com/young-geng/EasyLM
三、ColossalChat:深入體驗 RLHF 在大模型中的功能
ColossalChat[7] 是第一個基于LLaMA預訓練模型開源完整RLHF pipline實現,包括有監督數據收集、有監督微調、獎勵模型訓練和強化學習微調。只需要不到100億個參數,就可以在大型語言模型的基礎上通過RLHF微調達到中英文雙語水平,達到與ChatGPT和GPT-3.5相當的效果,并可以進行Demo測試。關于RLHF的原理,可參考
https://zhuanlan.zhihu.com/p/613315873
ColossalChat使用InstructionWild[8]雙語數據集,包含約52K的英語和52K的漢語問答,數據集通過OpenAI API接口獲得。該數據集適用于微調和RLHF訓練。通過提供高質量的數據,ColossalChat可以實現更好的對話互動,也可以支持中文。
數據集的獲取過程
3.1 監督指令微調
使用前面提到的數據集執行有監督指令微調,以微調模型。運行examples/train_sft.sh來啟動有監督的指令微調。
torchrun?--standalone?--nproc_per_node=4?train_sft.py? ????--pretrain?"/path/to/LLaMa-7B/"? ????--model?'llama'? ????--strategy?colossalai_zero2? ????--log_interval?10? ????--save_path??/path/to/Coati-7B? ????--dataset?/path/to/data.json? ????--batch_size?4? ????--accimulation_steps?8? ????--lr?2e-5? ????--max_datasets_size?512? ????--max_epochs?1?
3.2 訓練獎勵模型
訓練獎勵模型,通過手動對同一提示的不同輸出進行排序來分配相應的分數,然后有監督獎勵模型的訓練。
運行examples/train_rm.sh開始獎勵模型訓練。
torchrun?--standalone?--nproc_per_node=4?train_reward_model.py ????--pretrain?"/path/to/LLaMa-7B/"? ????--model?'llama'? ????--strategy?colossalai_zero2? ????--loss_fn?'log_exp' ????--save_path?'rmstatic.pt'?
3.3 人類反饋強化學習
在第一階段的監督微調模型和第二階段的獎勵模型的基礎上,使用強化學習算法進一步訓練大型語言模型。該階段是RLHF訓練的核心部分,在強化學習中使用近端策略優化(PPO)算法來引入獎勵信號,并生成更符合人類偏好的內容。
運行examples/train_prompts.sh,開始使用人類反饋訓練PPO。
torchrun?--standalone?--nproc_per_node=4?train_prompts.py?
?????????--pretrain?"/path/to/LLaMa-7B/"? ?????????--model?'llama'? ?????????--strategy?colossalai_zero2? ?????????--prompt_path?/path/to/your/prompt_dataset? ?????????--pretrain_dataset?/path/to/your/pretrain_dataset? ?????????--rm_pretrain?/your/pretrain/rm/defination? ?????????--rm_path?/your/rm/model/path
編輯:黃飛
?
評論
查看更多