本文是對 Andrej Karpathy 的在 2023 年 3 月份的 Microsoft Build 演講的整理。
演講 Beamer 可見於:https://karpathy.ai/stateofgpt.pdf
演講介紹了 GPT 的訓練過程,發展地步,當前的 LLM 生態以及未來展望,在一年後的今天也沒有過時,完全可以與當下的實際發展對比閱讀、分析。
概述#
pretraining 部分佔據了絕大部分訓練時間,後面的三個階段都是 fine-tuning 階段。
數據收集#
Training data mixture used in Meta's LLaMA model
Composition of the mixture:
- CommonCrawl: 普通的網絡爬蟲
- C4:Common Crawl 的一個巨大而乾淨的版本。
- 其它高質量數據集如圖所示
這些知識混合在一起,然後根據給定的比例進行採樣,構成了 GPT 神經網絡的訓練集。
預訓練#
實際訓練前,需要進行預處理步驟如下。
tokenization#
基本上是把互聯網上爬取的原始文本轉譯為整數序列(sequence of integers)的無損轉換過程。
可以使用像byte-pair encoding(BPE)的方法,迭代合併小文本塊並將它們分組為token
Transformer 神經網絡的超參數表格
-
Vocabulary Size(詞彙表大小):
- 詞彙表大小指的是模型能夠識別和生成的唯一詞彙(包括單詞、字符或子詞單元)的總數。這個數字定義了模型輸入和輸出的可能性範圍。
- 類比Bigram中,我們指定的是輸出預測的字母,因此是 “字符表”,大小為 27
-
Context Length(上下文長度):
- 上下文長度指的是模型在處理文本時能夠考慮的最大單元數(通常是詞或者 token)的數量。這個長度定義了模型在生成文本或理解文本時能夠回顧的信息量。
- NPLM模型中,上下文長度就被設為 3,也就是通過前 3 個 token 預測下一個。
- 如今 GPT4 等模型可以接受十萬多的輸入。
-
參數量(Parameters)
- 參數量指的是構成模型的參數的總數,這些參數在訓練過程中學習並調整,以最小化預測誤差。參數可以是權重(weights)和偏置(biases),它們在神經網絡中用於處理輸入數據,進行變換,並最終生成輸出。模型的參數量是衡量模型大小和複雜度的一個直接指標。
- NPLM中的這段代碼中就統計了模型的參數量,並嘗試了通過增加隱藏層神經元數等方式來加大參數量改善擬合。
g = torch.Generator().manual_seed(2147483647)
C = torch.randn((27,2), generator=g)
W1 = torch.randn((6,100), generator=g)
b1 = torch.randn(100, generator=g)
W2 = torch.randn((100,27), generator=g)
b2 = torch.randn(27, generator=g)
parameters = [C, W1, b1, W2, b2]
sum(p.nelement() for p in parameters)
- Training Tokens Total(訓練的 token 總量):
- 訓練的 token 總量指的是在訓練過程中模型處理的 token(可以是單詞、字符或子詞單元)的總數。這個數字反映了模型訓練過程中 “看到” 和學習的數據量。
- 類比姓名數據集中,一共有 30k 數據,那可以理解為 (1B 是,即十億)。
可以看到,LLaMA 的訓練量十分之大,用更長的訓練時間取得了比 GPT-3 更好的效果,因此不能只根據模型的參數量來判斷性能。
最開始的時候,模型的權重是隨機的,因此採樣結果是完全隨機的。隨著訓練時間增常,從模型中獲取的樣本就會越來越連貫而一致。從圖中最後可以看出,這個 GPT 模型已經學到了單詞、空格和標點符號等方面的知識。
訓練曲線#
隨著訓練進度推移,關注的重點是損失函數的變化,低損失意味著這個 Transformer 模型對序列中正確的下一個整數給予了更高的概率。
GPT 學習到了強大的general representations,也可以非常高效的去微調,適用於任意下游任務。
以情感分類任務為例子,我之前正好參與過相關研究,當時是調用百度的某個情感分析 API 來對我們收集到的數據進行積極、消極判斷等處理,得到監督學習中可以使用的數據,然後再用其它 NLP 模型進行訓練。但 GPT 出現後,完全可以先忽略情感分類去做 LLM 的預訓練,用少量的數據高效微調針對這一任務的 Transformer 模型。
這是因為 Transformer 模型在語言建模任務中被強制執行了大量的multitask,它被迫要了解文本的結構和其中所有不同的概念來預測下一個 token。這是 GPT-1 階段。
在 GPT-2 階段,人們注意到使用prompt(提示詞)實際上比微調更好、更有效。
基礎模型 ≠ 助手#
基礎模型並非我們平時使用的 ChatGPT,我們使用的是 GPT 模型的 api 如 Davinci、3.5 Turbo,它們是助手。而真正的基礎模型並不是assistant,只是想補全文件:
你可以通過創建特定的few-shot prompt來將基礎模型變為助手,讓它看看起來像是有一個中間的交互文檔,然後將你的查詢放在末尾,基礎模型就會自我調整為一個能幫忙的助手回答問題。但這不太可靠並且效果欠佳,所以創建實際的 GPT 助手走了一條不同的的路。
監督微調#
這個階段收集小而高質量的數據集,用眾包的形式,人工收集 prompt 和理想回應的數據。繼續對這些數據進行語言建模,算法不變,只是更換了數據集。訓練得到一個 SFT (Supervised Fine-Tuning) 模型,這是可部署的真正助手,有一定效果。
示意圖,眾包工人撰寫的回應被要求友好、真實和無害,並遵循著指示文件。
RLHF 管道#
acronym of reinforcement learning from human feedback
獎勵建模#
這個階段,我們將收集到的數據轉為Comparisons的形式,用相同的 prompt,來要求助手完成任務,讓訓練好的 SFT 模型創建多個版本的回答,再讓人們去評估哪個版本更好(這個很費時費力)
然後對這些版本進行分類,做法是在最後添加一個特殊的reward token,然後基本上只監督這個 (綠色) token 上用 Transformer。Transformer 會預測完成某個 prompt 的回答對應的獎勵,根據人工標註的真實獎勵標籤轉化為損失函數,然後訓練我們的模型,讓它產生和人工眾包的評估事實一致的對獎勵的預測。
建立好獎勵模型後,它本身作為助手還不是很有用,但是對接下來的強化學習階段十分有用。
強化學習#
根據獎勵模型,我們可以為任何給定 prompt 的 completion 完成質量打分。這個階段將針對獎勵模型來進行強化學習。
現在的訓練目標是 (黃色的) completion。使用 SFT 模型對不同 prompt 創建一些 completion,然後再次添加獎勵 token,根據已經固定的獎勵模型指示的獎勵來權衡語言建模目標。
圖中可以看出,高絕對值的 reward 會增加未來 token 採樣的權重。
在大量 prompt 和 batches 上迭代,獲得了能創建在獎勵模型中取得高分的 completion 的策略。
得到了可部署的 RLHF 模型。
為什麼 RLHF?#
表現更好,人類更喜歡它們生成的回答。
一種解釋可能:判斷比較和生成的難度是不對等的,比如相比於創作一個優秀的俳句(一種日本的古典短詩),判斷幾個俳句中哪個寫的更好顯然更簡單。這可以潛在地利用人類的判斷力,創建更好的模型。
但也因此,相較於 Basemodel,RLHF 後的模型失去了一些熵。也就是說模型輸出的變換很小,而 basemodel 具有很高的熵,並產生多種可能的輸出。因此在類似 “生成更多 Pokemon 名字” 的任務中,basemodel 也許更擅長。
應用 LLM 助手#
思維鏈#
aka COT
當人類寫作的時候,我們內心有一個獨立的過程 —— 總是在審視我們所寫的內容,並判斷寫的是否 good enough,我們可能刪掉一部分或者重新寫,然後對結果滿意。
而在 GPT 的視角,這只是一系列 token,它會查看每個 token 並在每個 token 上花費等量的計算,完全不會有上述的內心獨白。也就是說,Transformers 模型就相當於 token 模擬器,它們不知道自己善於或不擅長什麼,只是擬合下一個 token。模型不會對任何內容做反饋、合理性檢查或是糾錯。
GPT 通過存儲大量領域的基於事實的知識,用幾十億個參數存儲,擁有很強的工作記憶力。因此,在上下文長度範圍內的任何內容都可以通過 Transformer 內部的自注意力機制立即獲得,無損地記住這些內容。相當於是有限的完美記憶。
Prompting 只是彌補人腦和 “LLM 腦” 之間的認知差異的一種方式。因此實踐中,如果你在做需要推理能力的任務,你不能指望 Transformer 能對每個 token 都做太多推理,所以你必須將推理分散到更多 token 中。
讓 LLM 模擬這種推理
或者是多次採樣,然後投票選出答案
或者是我們生活中常用的:告訴 LLM 它的回答有錯誤,它會認識到錯誤。但如果你沒有提示他,他就根本不會自主反饋。
思維樹#
通過同時考慮多個潛在的可行計劃,並利用價值反饋機制進行決策,擴展了現有的規劃方法。此外,該方法還引入了自我反思機制,使語言模型能夠評估自身生成的候選項的可行性。
這是通過 python 粘合代碼 (Glue Code) 和單個 prompt 共同實現,其中還包括樹搜索等。
AlphaGo 就是模擬人類的決策,用蒙特卡洛樹搜索等評估所有可能性,然後保留那些好的選擇。
可以類比為針對文字的 AlphaGo。
人們開始探索更通用的技術,而不是單一的 prompt,更像是通過將很多 prompt 粘合在一起。
鏈 / 代理#
- ReAct:將對 prompt 的回答結構化為一系列 thought, action, observation, ... 的組合,用思考過程回答問題,這過程中模型也可以使用外部工具。
- AutoGPT:允許 LLM 保持任務列表並遞歸拆分完成任務的項目,表現一般但可以帶來一些啟發。
良好表現的條件#
提示工程#
LLM 其實有 “不想成功完成任務” 的 “心理怪癖”,它只是想模擬訓練集的數據,但你想完成任務,因此你要做出要求。
如:對於一個數學問題,訓練數據中可能有一個學生給出了錯誤答案,而一個數學專家給出了完美的答案,Transformers 無法區分哪個答案質量高。所以你必須要求它才能得到更好的表現。
聽上去可能很荒唐,這能讓 Transformers 現在不必將概率密度寄托在低質量的解決方案上
但也不要讓它有 “400 的 IQ”,這可能會得到科幻作品般的回答。
工具 / 插件#
LLM 默認情況下不知道自己不擅長什麼。
因此甚至可以在 prompt 中告訴它 “你不擅長計算”,計算的部分用這個 token 組合(如通過調用計算器 api 得到的)
檢索增強 LLMs#
搜索引擎是Retrieval only(只有檢索能力)的代表,也就是前 LLM 時代的主流。
而 LLM 則是Memory only,在兩個極端的之間存在很大的Retrieval augment(檢索增強)空間。
以 LlamaIndex 為例,它可以連接不同類型的數據,對這些數據建立索引並對 LLM 開放。
原理是將所給的文檔分成塊 (chunks),然後嵌入它們得到表示數據的嵌入向量 (embedding vectors),把它存儲在向量存儲庫中。提問時,會對向量存儲發出某種查詢,獲取可能與所提出的任務相關的塊,然後塞入 prompt 中再生成回答。實踐中效果很好。
可以類比,就算是一個記憶力出色的學生,但期末考試前還是會希望能去教材中找到具體原文。
約束提示#
這基本上是一些強制 LLMs 輸出特定模板的技術
下面例子中,我們強制要求 LLM 輸出 JSON 格式,然後可以對放入模板中這些空白處的內容強制實施額外限制。
Microsoft 的 “guidance” 項目
微調#
模型微調意味著改變模型的權重,一些技術讓這件事變得比以前更容易了。如 LoRA 可以確保你可以用低精度的推理(而不是梯度下降)只訓練模型中小而稀疏的部分(只有部分允許更改),做到有效微調,效果很好同時降低了成本。
建議#
建議分為針對兩個目標如下,也算是回顧了。
目標 1 得到最佳表現:
- 使用 GPT-4。
- 設計詳細任務上下文、相關信息和指令的提示(prompt)。
- 若無法通過電郵回覆,詢問任務承包人將會怎樣做。
- 為提示(prompt)添加任何相關的上下文或信息。
- 嘗試使用之前幻燈片中提到的提示工程技術(prompt engineering techniques)。
- 使用少數示例(few-shot examples)進行實驗,確保這些示例 1)與測試案例相關,2)多樣性(如果適當)。
- 使用工具 / 插件來卸載對於大型語言模型(LLMs)難以處理的任務(如計算、代碼執行等)。
- 質量時間優化流程 /“鏈(chains)”。
- 如果你對已經最大化了提示效用有信心,考慮收集 SFT 數據和 RLHF 微調(fine-tuning)。
目標 2 優化成本:
- 一旦實現了最高性能,嘗試節省成本的措施(例如使用更短的提示,GPT-3.5 等)。