👋

LoRAモデルをファインチューニングして「関西弁で返すLLM」を作り、Hugging Faceに公開してみた

に公開

はじめに

近年、大規模言語モデル(LLM)の進化は目覚ましく、様々なタスクで高い性能を発揮しています。しかし、特定の地域の方言やニュアンスを完全に捉えるには、さらなるカスタマイズが必要です。本記事では、Googleが開発した高性能なオープンモデルであるGemma 2 2B ITをベースに、LoRA(Low-Rank Adaptation)という効率的な手法を用いてファインチューニングを行い、関西弁で応答するLLMを開発し、その成果をHugging Faceに公開するまでのプロセスを技術的な視点から解説します。

開発したモデルは以下のURLで公開しています。

公開リポジトリ: hpscript/kansai_gemma_lora

1. プロジェクトの動機と概要

本プロジェクトの最大の動機は、標準語に偏りがちな既存のLLMに対し、日本の特定地域の方言である関西弁の対話能力を付与することでした。これにより、より親しみやすく、エンターテイメント性の高い対話システムを構築することを目指しました。

今回の開発の概要は以下の通りです。

  • 目標: 標準語の質問に対し、自然な関西弁で応答するLLMの実現
  • ベースモデル: google/gemma-2-2b-it
  • 手法: LoRA + 4bit量子化を用いたSFT (Supervised Fine-Tuning)
  • 公開先: Hugging Face Hub

2. 技術的な実装のエッセンス

今回のファインチューニングでは、限られた計算資源で効率的に学習を行うため、いくつかの重要な技術的工夫を取り入れました。

2.1. 4bit量子化によるメモリ節約

ベースモデルのロードには BitsAndBytesConfig を使用し、4bit量子化 (NF4) を適用しました。これにより、GPUメモリの消費を大幅に抑えつつ、モデルの性能低下を最小限に留めています。

  • NF4 (NormalFloat 4): 量子化タイプに採用し、メモリ効率を最大化。
  • Double Quantization: さらにメモリを節約するために有効化。
  • Compute Dtype: 計算には torch.float16 を使用。

2.2. LoRA (Low-Rank Adaptation) の設定

モデル全体を再学習するのではなく、特定の層に低ランク行列を導入するLoRAを採用しました。

  • ターゲットモジュール: Attention層の q_proj, k_proj, v_proj, o_proj を対象に設定。
  • ランク (r): 16
  • アルファ (lora_alpha): 32

この手法により、学習対象のパラメータ数を劇的に削減し、家庭用GPUレベルでも十分に学習が可能な構成にしています [2]。

2.3. 学習データのフォーマットとSFT

学習には trl ライブラリの SFTTrainer を使用しました。Gemma 2 ITモデルの性能を最大限に引き出すため、プロンプトは以下の形式(Chat Template)に準拠させています。

<start_of_turn>user
{標準語の入力}<end_of_turn>
<start_of_turn>model
{関西弁の応答}<end_of_turn>

このフォーマットで「おはよう」→「おはよう!今日もええ天気やな」といった対話ペアを学習させることで、モデルは「ユーザーの問いかけに対して関西弁で返す」というパターンを効率的に習得しました。

2.4. 最適化の工夫

学習の安定化と効率化のため、以下の設定を行いました。

  • Optimizer: paged_adamw_8bit を採用し、メモリ効率を向上。
  • Gradient Accumulation: ステップ数を調整し、実質的なバッチサイズを確保。
  • Learning Rate: 2e-4 前後の適切なレートを設定。

3. モデルの利用方法

Hugging Faceに公開されたLoRAアダプターは、ベースモデルと組み合わせて簡単に利用できます。

from transformers import AutoTokenizer, AutoModelForCausalLM
from peft import PeftModel
import torch

# ベースモデルとLoRAアダプターのロード
base_model_id = "google/gemma-2-2b-it"
model = AutoModelForCausalLM.from_pretrained(base_model_id, device_map="auto", torch_dtype=torch.bfloat16)
model = PeftModel.from_pretrained(model, "hpscript/kansai_gemma_lora")
tokenizer = AutoTokenizer.from_pretrained(base_model_id)

# テキスト生成(詳細はリポジトリのModel Cardを参照)

4. 関西弁LLMのテスト結果

実際にファインチューニングされたモデルに対し、いくつかの対話テストを実施しました。結果は以下の通りで、自然で親しみやすい関西弁での応答が確認できました。

テスト1: 挨拶

user: おはよう
model: おはよう!今日もいい天気やな

評価: 挨拶と天気の話題を関西弁で自然に継続しています。

テスト2: 感謝

user: ありがとう
model: ありがとうな!助かったわ

評価: 感謝の気持ちを関西弁の「な」「わ」で表現しており、親近感があります。

テスト3: 感嘆

user: すごいですね
model: すごいわ!まじで感動したな!

評価: 感嘆の表現が強調され、感情が伝わる応答です。

テスト4: 天気の話題

user: 今日はいい天気ですね
model: 今日天気最高やな

評価: 丁寧語の問いかけに対し、カジュアルな関西弁に変換して応答する能力が確認できました。

5. Hugging Faceへの公開手順

学習が完了し、満足のいく結果が得られたら、以下の手順でLoRAアダプターをHugging Face Hubに公開します。

5.1. ログイン

まず、Hugging Faceのトークンを使用してログインします。

from huggingface_hub import login
login(token="YOUR_HUGGINGFACE_TOKEN")

5.2. モデルのアップロード

学習済みの trainer オブジェクトには、モデルをHubにプッシュするための便利なメソッドが用意されています。

# trainer.train() の後に実行
repo_id = "username/kansai_gemma_lora" # 公開するリポジトリ名
trainer.model.push_to_hub(repo_id)
trainer.tokenizer.push_to_hub(repo_id)

この操作により、LoRAアダプターの重みファイルとトークナイザーの設定が指定したリポジトリにアップロードされ、世界中の誰もがあなたのモデルを利用できるようになります。

6. まとめと今後の展望

本プロジェクトでは、4bit量子化とLoRAを組み合わせることで、軽量かつ高性能な関西弁LLMを実現しました。

今回のポイント:

  • Gemma 2 2B IT の対話能力をベースに活用。
  • SFTTrainer と適切なプロンプトフォーマットによる効率的な学習。
  • Hugging Face Hub での公開によるコミュニティへの還元。

今後は、より多様なシチュエーション(ビジネス、専門分野など)での関西弁対応や、他の地域の方言モデルへの応用も検討していきたいと考えています。


参考文献

[1] Google. Gemma 2: Open Models from Google. https://blog.google/technology/developers/gemma-2-open-models/
[2] Hu, E. J., et al. (2021). LoRA: Low-Rank Adaptation of Large Language Models. arXiv preprint arXiv:2106.09685.
[3] Hugging Face. PEFT: Parameter-Efficient Fine-Tuning. https://huggingface.co/docs/peft/index

Discussion