見出し画像

WSL2でLLM-jp-3-*-instructをvLLMと共に試してみる

「オープンかつ日本語に強いGPT-3級大規模言語モデル「LLM-jp-3 172B」の事前学習に使用しているコーパスで学習した 1.8B、3.7B、13B の各モデルを公開」したらしいので試してみます。

それぞれのモデル毎に、ベースとinstruct の各モデルが公開されています。今回はinstructのモデル3つを試します。

使用するPCはドスパラさんの「GALLERIA UL9C-R49」。スペックは
・CPU: Intel® Core™ i9-13900HX Processor
・Mem: 64 GB
・GPU: NVIDIA® GeForce RTX™ 4090 Laptop GPU(16GB)
・GPU: NVIDIA® GeForce RTX™ 4090 (24GB)
・OS: Ubuntu22.04 on WSL2(Windows 11)
です。


1. 準備

仮想環境

python3 -m venv vllm
cd $_
source bin/activate

つづいて、パッケージのインストール。

pip install -U vllm

vLLMのインストール時にtorchやら依存関係必要なものは勝手にインストールされます。

2. 流し込むコード

こちらを/path/to/query4vllm.pyとして保存します。

import sys
import argparse
from vllm import LLM, SamplingParams
from typing import List, Dict
import time

# argv
parser = argparse.ArgumentParser()
parser.add_argument("--model-path", type=str, default=None)
parser.add_argument("--no-chat", action='store_true')
parser.add_argument("--no-use-system-prompt", action='store_true')
parser.add_argument("--max-model-len", type=int, default=32768)
parser.add_argument("--tensor-parallel-size", type=int, default=1)
parser.add_argument("--gpu-memory-utilization", type=float, default=0.2)
parser.add_argument("--max-tokens", type=int, default=4096)

args = parser.parse_args(sys.argv[1:])

model_id = args.model_path
if model_id == None:
    exit

is_chat = not args.no_chat
use_system_prompt = not args.no_use_system_prompt
max_new_tokens = args.max_tokens
tensor_parallel_size = args.tensor_parallel_size
max_model_len = args.max_model_len
gpu_memory_utilization = args.gpu_memory_utilization

# トークナイザーとモデルの準備
model = LLM(
    model=model_id,
    dtype="auto",
    trust_remote_code=True,
    tensor_parallel_size=tensor_parallel_size,
    max_model_len=max_model_len,
    #quantization="awq",
    gpu_memory_utilization=gpu_memory_utilization
)
tokenizer = model.get_tokenizer()

DEFAULT_SYSTEM_PROMPT = "あなたは誠実で優秀な日本人のアシスタントです。"

def q(
    user_query: str,
    history: List[Dict[str, str]]=None
) -> List[Dict[str, str]]:
    # generation params
    generation_params = SamplingParams(
        temperature=0.8,
        top_p=0.95,
        top_k=40,
        max_tokens=max_new_tokens,
        repetition_penalty=1.1
    )
    #
    start = time.process_time()
    # messages
    messages = ""
    if is_chat:
        messages = []
        if use_system_prompt:
            messages = [
                {"role": "system", "content": DEFAULT_SYSTEM_PROMPT},
            ]
        user_messages = [
            {"role": "user", "content": user_query}
        ]
    else:
        user_messages = user_query
    if history:
        user_messages = history + user_messages
    messages += user_messages
    # generation prompts
    if is_chat:
        prompt = tokenizer.apply_chat_template(
            conversation=messages,
            add_generation_prompt=True,
            tokenize=False
        )
    else:
        prompt = messages
    input_ids = tokenizer.encode(
        prompt,
        add_special_tokens=True,
    )
    print("--- prompt")
    print(prompt)
    print("--- output")
    # 推論
    outputs = model.generate(
        sampling_params=generation_params,
        prompt_token_ids=[input_ids],
    )
    print(outputs)
    output = outputs[0]
    print(output.outputs[0].text)
    if is_chat:
        user_messages.append(
            {"role": "assistant", "content": output.outputs[0].text}
        )
    else:
        user_messages += output.outputs[0].text
    end = time.process_time()
    ##
    input_tokens = len(output.prompt_token_ids)
    output_tokens = len(output.outputs[0].token_ids)
    total_time = end - start
    tps = output_tokens / total_time
    print(f"prompt tokens = {input_tokens:.7g}")
    print(f"output tokens = {output_tokens:.7g} ({tps:f} [tps])")
    print(f"   total time = {total_time:f} [s]")
    return user_messages

3. 試してみる

(1) llm-jp/llm-jp-3-1.8b-instruct

1.8Bモデルに聞いてみます。

CUDA_VISIBLE_DEVICES=0 python -i /path/to/query4vllm.py \
    --model-path llm-jp/llm-jp-3-1.8b-instruct \
    --max-model-len 4096 \
    --gpu-memory-utilization 0.99

pythonプロンプトが表示されたら、聞きましょう。

>>> history = q("ドラえもんとはなにか")
--- prompt
<s>以下は、タスクを説明する指示です。要求を適切に満たす応答を書きなさい。

### 指示:
ドラえもんとはなにか

### 応答:

--- output
Processed prompts: 100%|███████████████████| 1/1 [00:02<00:00,  2.47s/it, est. speed input: 14.99 toks/s, output: 149.07 toks/s]

「ドラえもん」とは、藤子・F・不二雄による日本の漫画およびそれらを原作としたアニメ作品のタイトルです。物語は22世紀から来たネコ型ロボットであるドラえもんと、22世紀の未来から現代の地球にやってきたのび太という小学生男子が、さまざまな問題や困難を解決しながら友情を育んでいく姿を描いています。

物語の中心には、のび太という普通の小学生がいます。彼は勉強もスポーツも苦手ですが、正義感があり、仲間思いの人物です。ある日、ドラミという謎めいた少女が現れ、のび太を助けるためにタイムマシンを使って未来からドラえもんを持ってきました。ドラえもんは、どこでもドアやタケコプターなど、多くのひみつ道具を持っており、これらを使ってのび太たちは様々な冒険を繰り広げます。

ドラえもんの世界は、科学技術が進歩しているものの、人々の心はまだ豊かで、自然との調和も大切にされています。そのため、のび太たちにとって現実世界での教訓となるようなシーンも多いです。また、友情や努力、思いやりといったテーマが重要な要素として描かれており、子どもから大人まで幅広い層に支持されています。

登場キャラクターとしては、のび太はもちろんのこと、ジャイアン(剛田武)やスネ夫(骨川スネ夫)など個性的な同級生たちが登場し、それぞれが異なる魅力を持っています。特にジャイアンはその巨体と力強さで知られ、彼の言動や行動には思わず笑ってしまうことが多いです。

アニメ版ではテレビ朝日系列で放送されており、日本国内のみならず海外でも高い人気を誇っています。また、映画版も数多く制作され、毎年新たなエピソードやストーリーが展開されています。特に劇場版第5作『 のび太の魔界大冒険』では、魔法という概念が取り入れられるなど、原作とは一味違った世界観が楽しめます。

このように、「ドラえもん」は単なるアニメ作品にとどまらず、文化的にも社会的にも非常に大きな影響を持つ作品となっています。

llm-jp/llm-jp-3-1.8b-instruct
prompt tokens = 37
output tokens = 368 (147.064601 [tps])
   total time = 2.502302 [s]

ドラミちゃんが少女になっていますが、1.8Bでこの内容はいいんじゃないでしょうか。推論もちょー速いですし。

(2) llm-jp/llm-jp-3-3.7b-instruct

3.7Bモデルに聞いてみます。

CUDA_VISIBLE_DEVICES=0 python -i /path/to/query4vllm.py \
    --model-path llm-jp/llm-jp-3-3.7b-instruct \
    --max-model-len 4096 \
    --gpu-memory-utilization 0.99

pythonプロンプトが表示されたら、聞きましょう。

>>> history = q("ドラえもんとはなにか")
--- prompt
<s>以下は、タスクを説明する指示です。要求を適切に満たす応答を書きなさい。

### 指示:
ドラえもんとはなにか

### 応答:

--- output
Processed prompts: 100%|█████████████████████| 1/1 [00:06<00:00,  6.47s/it, est. speed input: 5.72 toks/s, output: 91.26 toks/s]

「ドラえもん」とは、藤子・F・不二雄による日本の漫画およびアニメシリーズ、およびそれに登場するキャラクターの名前です。以下に、「ドラえもん」について詳しく説明します。

### 1. 概要
「ドラえもん」は未来から来たネコ型ロボットで、のび太という少年の家で一緒に暮らしています。のび太が困ったときに助けてくれる存在であり、彼らの冒険や友情、そして成長を描いた物語です。

### 2. キャラクター紹介
- ドラえもん (Doraemon): 声 - 大山のぶ代(第1作)、水田わさび(現在)
未来から来たネコ型ロボット。青い体と長い耳が特徴。四次元ポケットから様々な道具を使ってのび太たちをサポートする。

- 野比のび太(のび のびた): 声 - 小原乃梨子(第1作)、関智一(現在)
のび太くんの愛称。勉強もスポーツも苦手だが、心優しい性格。ドラえもんと共に数々の困難を乗り越える。

- 源しずか(みなもと しずか): 声 - 野村道子(第1作)、かかずゆみ(現在)
ノビタオーラ号の持ち主であり、のび太のクラスメイト。とても優しく、心の強い少女。

- 骨川スネ夫(ほねかわ スネオ): 声 - 肝付兼太(第1作)、関智一(現在)
富豪の息子で、プライドが高く自信過剰な性格だが、根は悪い人ではない。ジャイアンとよくつるむ。

### 3. ストーリーライン
「ドラえもん」は子供向けの作品ですが、そのテーマは非常に幅広く、多くのエピソードがあります。主なストーリーラインには以下のようなものがあります:

1. 日常生活でのトラブル解決:
- 宿題ができない、テストで失敗する、友達関係などで悩むのび太のために、ドラえもんが様々なひみつ道具を出して問題を解決します。

2. 冒険と探検:
- タイムマシン、瞬間移動機、透明になる薬など、さまざまなアイテムを使って異世界や未知の世界への冒険に出かけます。

3. 友情と家族愛:
- のび太とその仲間たちとの絆や、親との関係を深めるエピソードもあります。

4. 社会風刺と教育的要素:
- 現代社会の問題点やモラルについて考えさせられる内容もあり、大人でも楽しめる要素があります。

### 4. アニメ化と映画版
- テレビアニメ: 1979年に放送が開始され、現在も新作が制作されています。日本のみならず世界中で人気があり、多くの国で放映されています。
- 映画: 1979年の第一作以降、毎年夏に新作が公開されており、特に1979年の『ドラえもん のび太の恐竜』、2005年の『ドラえもん のび太の恐竜2006』などが有名です。

以上が、「ドラえもん」についての基本的な情報です。この作品は世代を超えて愛され続けており、多くの人々に影響を与えてきました。

llm-jp/llm-jp-3-3.7b-instruct
prompt tokens = 37
output tokens = 590 (90.673710 [tps])
   total time = 6.506847 [s]

ノビタオーラ号、宝島ですな。

(3) llm-jp/llm-jp-3-13b-instruct

config.json のパラメータ値を確認しつつ、起動します。
13Bモデルですと1x24GBでは足りませんので、tensor-parallel-sizeを2としてGPUを2枚使用します。

CUDA_VISIBLE_DEVICES=0,1 python -i /path/to/query4vllm.py \
    --model-path llm-jp/llm-jp-3-13b-instruct \
    --max-model-len 4096 \
    --tensor-parallel-size 2 \
    --gpu-memory-utilization 0.95

聞いてみましょう。

>>> history = q("ドラえもんとはなにか")
--- prompt
<s>以下は、タスクを説明する指示です。要求を適切に満たす応答を書きなさい。

### 指示:
ドラえもんとはなにか

### 応答:

--- output
Processed prompts: 100%|█████████████████████| 1/1 [00:18<00:00, 18.05s/it, est. speed input: 2.05 toks/s, output: 24.04 toks/s]

「ドラえもん」は、藤子・F・不二雄による日本の漫画作品、およびその主人公の名前です。以下は、その要点です:

1. 概要:
- 「ドラえもん」(正式名称:DORAEMON)は、1969年から1996年まで連載された児童向けSFコメディ漫画で、22世紀からやってきたネコ型ロボットのドラえもんと、勉強もスポーツも苦手な小学生ののび太とその仲間たちの日常生活が描かれています。

2. 主な登場人物:
- ドラえもん (Doraemon): 2112年9月3日生まれのネコ型ロボット。野比のび太のもとへ未来のお手伝いロボットとしてやってくる。四次元ポケットを持っており、さまざまなひみつ道具を出すことができる。
- 野比のび太 (Nobi Nobita): 勉強も運動も苦手な小学生。ドラえもんと一緒に冒険し、成長していく。
- しずかちゃん (Sister Sugich) / 源静香 (Moto Shizuka): のび太のクラスメイトでマドンナ的存在。バイオリンが得意。
- ジャイアン (Gian): のび太のクラスメイトでガキ大将。歌が上手だが、時々暴力的になる。
- スネ夫 (Sunao Kaoru): のび太のもう一人の親友。裕福な家庭に育ち、最新のおもちゃを持っている。

3. ストーリー展開:
- 物語の大部分は、のび太とドラえもんの友情を中心に、彼らが様々なトラブルや困難に立ち向かう様子が描かれる。また、日常の中にちょっとした冒険や感動的なエピソードが盛り込まれている。

4. テーマとメッセージ:
- 友情、家族愛、努力、勇気といった普遍的なテーマが描かれており、読者に希望や勇気を与える内容が多い。特にのび太の成長過程や、失敗しても諦めずに頑張る姿勢が強調されることが多い。

5. メディア展開:
- 漫画だけでなく、アニメ化され、映画シリーズとしても広く親しまれている。また、玩具やゲーム、グッズなども多数販売されている。

「ドラえもん」はその親しみやすいキャラクターと魅力的なストーリーテリングによって、世代を超えて多くの人々に愛され続けています。

llm-jp/llm-jp-3-13b-instruct
prompt tokens = 37
output tokens = 434 (23.939246 [tps])
   total time = 18.129226 [s]

4. まとめ

1.8Bモデルもとてもいいかんじ。他のモデルもきちんとドラえもんのことを学習しているように見えます。すばらしい。

いいなと思ったら応援しよう!