Negi Labの諸君、遊びは終わりだ。 「ChatGPTを使えば十分」という甘い考えは捨てろ。特定のドメインや社内データに特化した「自分たちのモデル」を持ってこそ、エンジニアとしての価値がある。
今日は、計算リソースを最小限に抑えつつ、モデルの性能を劇的に変化させる「LoRA(Low-Rank Adaptation)」の構築手順を叩き込む。リソースをドブに捨てるような非効率な学習は、今日限りで卒業してもらおう。
この記事で学べること
- LoRAを動作させるためのモダンなライブラリ構成と環境構築
- 精度と計算コストを両立させるハイパーパラメータの決定方法
- 実行時に遭遇するVRAM不足や学習の失敗を回避する実戦的テクニック
前提条件
- ハードウェア: NVIDIA GPU(VRAM 16GB以上推奨。12GBでも4-bit量子化で対応可能だが、速度は妥協することになる)
- OS: Linux (Ubuntu 20.04+) 推奨。WSL2でも可。
- Python: 3.10以上。
Step 1: 環境準備
まずは足場固めだ。ライブラリのバージョン不整合で時間を溶かすのは素人のすることだ。以下の構成を正確にインストールしろ。
# 仮想環境の作成
python3 -m venv venv
source venv/bin/activate
# 依存ライブラリのインストール
# PEFT (Parameter-Efficient Fine-Tuning) は必須だ
pip install torch torchvision torchaudio --index-url https://download.pytorch.org/whl/cu118
pip install transformers accelerate bitsandbytes peft datasets trl
特に bitsandbytes は量子化に、peft はLoRAのコア実装に必要だ。これを忘れると、お前のGPUは一瞬でメモリ不足(OOM)で悲鳴を上げることになる。
Step 2: 基本設定
次にLoRAの核心となる設定(LoraConfig)を記述する。
ここでは、モデルのどの層にアダプタを差し込むかが重要だ。通常は q_proj と v_proj を狙うが、最近のトレンドでは全線形層を対象にすることもある。
from peft import LoraConfig, get_peft_model
from transformers import AutoModelForCausalLM, BitsAndBytesConfig
import torch
# 1. 量子化設定(4-bitでVRAMを節約)
bnb_config = BitsAndBytesConfig(
load_in_4bit=True,
bnb_4bit_quant_type="nf4",
bnb_4bit_compute_dtype=torch.bfloat16,
bnb_4bit_use_double_quant=True,
)
# 2. ベースモデルのロード
model_id = "llm-jp/llm-jp-3-13b" # 例としてLLM-jpを使用
model = AutoModelForCausalLM.from_pretrained(
model_id,
quantization_config=bnb_config,
device_map="auto"
)
# 3. LoRA設定
# r(Rank)は8〜64が一般的。大きくしすぎるとオーバーフィッティングのリスクが高まる
config = LoraConfig(
r=16,
lora_alpha=32,
target_modules=["q_proj", "v_proj", "k_proj", "o_proj"],
lora_dropout=0.05,
bias="none",
task_type="CAUSAL_LM"
)
# LoRAモデルへの変換
model = get_peft_model(model, config)
model.print_trainable_parameters()
lora_alpha は通常 r の2倍に設定するのが定石だ。スケーリングの安定性が増す。
Step 3: 実行と確認
学習には trl ライブラリの SFTTrainer を使うのが、コードの記述量を減らしミスを防ぐ最短ルートだ。
from trl import SFTTrainer
from transformers import TrainingArguments
# 学習引数の設定
training_args = TrainingArguments(
output_dir="./output-lora",
per_device_train_batch_size=4,
gradient_accumulation_steps=4,
learning_rate=2e-4,
num_train_epochs=3,
logging_steps=10,
save_strategy="epoch",
fp16=True, # GPUに合わせてbf16と使い分けろ
push_to_hub=False,
report_to="none"
)
# トレーナーの初期化
trainer = SFTTrainer(
model=model,
train_dataset=your_dataset, # 事前にロードしたdatasets形式のデータ
dataset_text_field="text",
max_seq_length=512,
args=training_args,
)
# 学習開始
trainer.train()
学習が終わったら、model.save_pretrained("./final-lora-adapter") でアダプタのみを保存する。ベースモデルと合わせても数十MB程度だ。これがLoRAの美しさだ。
よくあるエラーと対処法
エラー1: CUDA Out of Memory (OOM)
torch.cuda.OutOfMemoryError: CUDA out of memory. Tried to allocate ...
解決策:
per_device_train_batch_sizeを 1 に下げ、その分gradient_accumulation_stepsを増やせ。max_seq_lengthを短く設定し直せ。BitsAndBytesConfigで4-bit量子化が有効になっているか再確認しろ。
エラー2: 学習が進まない(Lossが減らない)
解決策:
- 学習率(
learning_rate)が高すぎないか? LLMの微調整には2e-4や5e-5あたりが適正だ。 - データセットのフォーマット(プロンプトテンプレート)がモデルの期待するものと一致しているか確認しろ。
まとめと次のステップ
おめでとう。これで君も「LoRAを理解している側」の人間だ。 だが、これは始まりに過ぎない。
次にやるべきことは以下の3点だ:
- DPO(Direct Preference Optimization): 生成AIの「好み」を調整し、より人間らしい回答をさせる。
- 評価パイプラインの構築: 自分のモデルが「本当に賢くなったのか」を定量的に測定する。
- 推論の高速化: vLLMやTGIを使って、作成したアダプタを実サービスに耐えうる速度でデプロイする。
Negi Labでは、実戦で使えない技術に興味はない。手を動かし、ログを読み、モデルを極めろ。
関連商品をチェック
※上記リンクはアフィリエイトリンクです。購入により当サイトに収益が発生する場合があります。






