はじめに
Llama2ベースのモデルをLoRAなどで追加学習したオリジナルモデルを、量子化してGGUF形式として保存する流れを備忘録としてまとめました。
1. ベースモデルとLoRAを統合する
from peft import PeftModel
from transformers import AutoModelForCausalLM, LlamaTokenizer
# ベースモデルの読み込み
tokenizer = LlamaTokenizer.from_pretrained(model_name)
model = AutoModelForCausalLM.from_pretrained(model_name, device_map="auto")
model.resize_token_embeddings(len(tokenizer))
# LoRAの反映
model = PeftModel.from_pretrained(
model,
lora_adapter_dir,
device_map={"":0}
)
model.eval()
# 統合したモデルの保存(HuggingFace形式)
merged_model = model.merge_and_unload()
merged_model.save_pretrained(output_dir)
tokenizer.save_pretrained(output_dir)
2. Llama.cppの導入
npakaさんのこちらの記事を参考にさせていただきました。
Windowsでは、以下のC/C++ビルドツールを導入しておきます。
bin配下を環境変数に登録し、以下を実行してLlama.cppをビルドします。
git clone https://github.com/ggerganov/llama.cpp
cd llama.cpp
make
少し待つと、Llama.cppフォルダの中に実行可能形式(.exe)が保存されます。エラーが発生せず問題なくビルドできれば完了です。
3. HuggingFace形式からGGUF形式に変換
数ビットに量子化する前に、一旦32ビット/16ビット/8ビットに変換をかけます。
今回は実質的に損失がない16ビットを選択しました。--outtype
は、f32
, f16
, q8
から選択できます。
python convert.py path/to/original_model_HF/ --outtype f16
変換が終了すると、ggml-model-f16.gguf
というファイル名でGGUFファイルが保存されます。
4. 数ビットに量子化
ビルドしてできた「quantize.exe」を利用して、ggml-model-f16.gguf
を量子化します。
quantize path/to/original_model_HF/ggml-model-f16.gguf Q5_K_M
量子化のビット数、手法の表記は以下から選択できます。
Allowed quantization types:
2 or Q4_0 : 3.56G, +0.2166 ppl @ LLaMA-v1-7B
3 or Q4_1 : 3.90G, +0.1585 ppl @ LLaMA-v1-7B
8 or Q5_0 : 4.33G, +0.0683 ppl @ LLaMA-v1-7B
9 or Q5_1 : 4.70G, +0.0349 ppl @ LLaMA-v1-7B
10 or Q2_K : 2.63G, +0.6717 ppl @ LLaMA-v1-7B
12 or Q3_K : alias for Q3_K_M
11 or Q3_K_S : 2.75G, +0.5551 ppl @ LLaMA-v1-7B
12 or Q3_K_M : 3.07G, +0.2496 ppl @ LLaMA-v1-7B
13 or Q3_K_L : 3.35G, +0.1764 ppl @ LLaMA-v1-7B
15 or Q4_K : alias for Q4_K_M
14 or Q4_K_S : 3.59G, +0.0992 ppl @ LLaMA-v1-7B
15 or Q4_K_M : 3.80G, +0.0532 ppl @ LLaMA-v1-7B
17 or Q5_K : alias for Q5_K_M
16 or Q5_K_S : 4.33G, +0.0400 ppl @ LLaMA-v1-7B
17 or Q5_K_M : 4.45G, +0.0122 ppl @ LLaMA-v1-7B
18 or Q6_K : 5.15G, -0.0008 ppl @ LLaMA-v1-7B
7 or Q8_0 : 6.70G, +0.0004 ppl @ LLaMA-v1-7B
1 or F16 : 13.00G @ 7B
0 or F32 : 26.00G @ 7B
COPY : only copy tensors, no quantizing
量子化が完了し、ggml-model-Q5_K_M.gguf
など正常にGGUFファイルが保存されていることを確認したら完了です。
5. 量子化モデルを使って推論
Llama.cppを動作させるためのPythonライブラリをインストールします。
pip install llama-cpp-python
「houou-7b」に合わせたプロンプトの場合は以下のようになります。
from llama_cpp import Llama
llm = Llama(model_path="path/to/original_model_HF/ggml-model-Q5_K_M.gguf")
instruction = "日本のおすすめの観光地を3つ教えてください。"
input = ""
if input == "":
prompt = f"""
以下は、タスクを説明する指示です。要求を適切に満たす応答を書きなさい。
### 指示:
{instruction}
### 応答:
"""
else:
prompt = f"""
以下は、タスクを説明する指示と、文脈のある入力の組み合わせです。要求を適切に満たす応答を書きなさい。
### 指示:
{instruction}
### 入力:
{input}
### 応答:
"""
output = llm(
prompt,
temperature=0.5,
stop=["### 指示:", "### 入力:", "### 応答:", "\n"],
echo=True,
)
print(output["choices"][0]["text"])