マガジン

ローカルAIの返答が遅いとき:生成速度の測り方と見直す順番

AIを使いこなす

Claudeで執筆し、GPTで自動校閲・修正しています。

ノートPCの横で無地のカードを順番に並べる手元
記事の内容をもとに制作したAI生成イメージです。実際の製品画面や検証結果の写真ではありません。

結論から言うと、「遅い」を一つの症状として扱わず、モデルの読み込み待ち・入力の処理待ち・文章の生成速度に分けて数字にします。そのうえで、ollama ps でモデルがGPUに載っているかを最初に確認し、次にコンテキスト長、モデルの大きさ、の順に一つずつ変えて同じ質問で測り直すのが、遠回りになりにくい進め方です。 Ollamaは、生成が終わったときのレスポンスに所要時間と処理したトークン数を含めます。APIの利用統計のページでは、時間はナノ秒単位で、load_duration(モデルの読み込み)、prompt_eval_duration(キャッシュされていない入力トークンの評価)、eval_duration(出力の生成)、eval_count(出力トークン数)などが返ると説明されています。生成速度は eval_count ÷ (eval_duration ÷ 10億) で、1秒あたりの出力トークン数として計算できます。この計算式自体はそのページに明記されたものではなく、各項目の定義から導いた計算です。 この記事の手順と数値の例は、執筆時点で実機では実行していません。表の数字はすべて「説明用の例」で、実測ではありません。公式ドキュメントは2026年10月29日の自動校閲時に本文を確認しました。

この記事の目次
  1. 同じ質問で測る:コマンドと条件の固定
  2. 記録表:変更ごとに1行ずつ残す
  3. 見直す順番:影響が大きそうなものから
  4. 測定結果から次の一手を決める判断表
  5. AIに記録表の読み解きを頼むときの依頼文

同じ質問で測る:コマンドと条件の固定

体感では、長い回答を待つと遅く、短い回答だと速く感じます。そこで、条件をそろえて「1秒あたり何トークン出ているか」を見ます。

測定用のコマンド例

macOS/Linuxのターミナルで、jq が入っている前提の例です。MODEL名 は ollama list に出ているものに置き換えてください。

bash
curl -s http://localhost:11434/api/generate -d '{
  "model": "MODEL名",
  "prompt": "ローカルAIを使う利点と注意点を、箇条書き5点で説明してください。",
  "stream": false,
  "options": { "temperature": 0, "seed": 42 }
}' | jq '{
  load_s: (.load_duration / 1e9),
  prompt_eval_s: (.prompt_eval_duration / 1e9),
  output_tokens: .eval_count,
  eval_s: (.eval_duration / 1e9),
  gen_tokens_per_s: (if .eval_duration > 0 then (.eval_count / (.eval_duration / 1e9)) else null end)
}'

生成APIのページにある stream: false で、回答と統計が一つのJSONとして返ります。temperature と seed はModelfileのパラメータ一覧に説明がある生成設定で、回答の揺れを減らす目的で固定しています。揺れが完全になくなるとは限らないので、後述のとおり複数回測ります。

固定する条件

  • 質問文は毎回この一文(または自分の用途に近い一文)に固定する
  • 測定の前に何も重い作業をしない(ブラウザの動画、ゲーム、別のAIアプリなど)
  • 1回目は準備として実行し、モデルがメモリに残っている間に続けて測った2回目以降の数値を記録する
  • 同じ条件で3回測り、中央の値を使う
  • 一度に変える設定は一つだけにする

機密を含む文章は、測定にそのまま使わないでください。速度比較には架空の文章で十分です。

記録表:変更ごとに1行ずつ残す

次の表をそのままコピーして使えます。下の数字は説明用の例で、実測ではありません。

  • 0、変更した点:変更なし(基準)、モデル:model-A、PROCESSOR:52%/48% CPU/GPU、CONTEXT:4096、load_s:0.1、prompt_eval_s:0.3、出力トークン:240、eval_s:40.0、gen_tokens_per_s:6.0、気づいたこと:例:CPUに分散している
  • 1、変更した点:他のモデルを停止、モデル:model-A、PROCESSOR:100% GPU、CONTEXT:4096、load_s:0.1、prompt_eval_s:0.2、出力トークン:238、eval_s:8.5、gen_tokens_per_s:28.0、気づいたこと:例:GPUに収まった
  • 2、変更した点:コンテキスト長を下げた、モデル:model-A、PROCESSOR:100% GPU、CONTEXT:2048、load_s:0.1、prompt_eval_s:0.2、出力トークン:245、eval_s:8.45、gen_tokens_per_s:29.0、気づいたこと:例:差は小さい

読み方は単純です。gen_tokens_per_s が上がり、回答の質に不満がなければ、その変更を残します。変更後に速度が変わらなければ元に戻して、次の項目へ進みます。PROCESSORとCONTEXTは ollama ps の列で、取得方法は次の節で説明します。

見直す順番:影響が大きそうなものから

以下の並びは、コンテキスト長のページが性能のためにCPUへのオフロードを避けるよう案内していることを踏まえ、メモリ配置から確認する編集上の提案です。速度への効き方は環境で変わるので、各ステップの後に必ず表へ記録してください。

  1. ollama ps でGPUに載っているか確認する。 FAQによると、PROCESSOR 列に 100% GPU、100% CPU、または 48%/52% CPU/GPU のように、読み込み先の割合が表示されます。CPUの割合が大きいなら、モデルがGPUメモリに収まっていない可能性があります。ただし、この表示だけで遅さの原因は確定できません。100% CPU で対応GPUを使う予定なら、トラブルシューティングを参照してログを確認します。NVIDIAではドライバの更新状況、LinuxのAMDでは権限やドライバの互換性も確認します。
  2. 別のモデルが残っていないか確認する。 ollama ps に複数のモデルが並んでいたら、使わないものを ollama stop モデル名 で止めて測り直します。FAQには同時にロードできるモデル数の設定(OLLAMA_MAX_LOADED_MODELS)もあり、メモリを他のモデルと取り合っている可能性があります。
  3. コンテキスト長を確認し、必要以上に大きければ下げる。 ollama ps の CONTEXT 列で割り当てを確認できます。コンテキスト長のページでは、大きなコンテキスト長ほど必要なメモリが増えると説明されています。既定値の記述は公式ページ間で異なるため、実際の割り当ては手元の CONTEXT 列で確認してください。今回のAPI測定だけ変更するなら、options に "num_ctx": 2048 などを加えます。サーバー全体の既定値は、手動起動なら OLLAMA_CONTEXT_LENGTH=8192 ollama serve のように指定できます。すでにアプリやサービスが起動している場合は、FAQのOS別設定方法に従って環境変数を設定し、再起動して反映します。長い文書を扱う用途なら、むやみに下げず、必要な長さだけにとどめます。
  4. モデルを小さくするか、量子化の強いものに替える。 同じ系列でパラメータ数の小さい版や、量子化の強い版を比較候補にします。これは編集上の試行案で、速度が上がるという保証ではありません。モデルを替えるとトークンの区切り方も異なる場合があるため、トークン/秒だけで優劣を決めず、同じ質問への回答時間と質も確かめてください。
  5. FlashAttentionとKVキャッシュの設定を確認する。 FAQでは、FlashAttentionはバックエンドとデバイスが対応していれば自動で使われ、OLLAMA_FLASH_ATTENTION=1 は強制的に有効化する指定とされています。KVキャッシュの量子化はFlashAttentionが有効な場合に利用でき、OLLAMA_KV_CACHE_TYPE で f16・q8_0・q4_0 から選べます。これらもサーバー側の環境変数として設定し、再起動して反映します。主な狙いはメモリ使用量の削減です。メモリが足りずCPUに回っていた場合に、結果として速度が改善するかを表で確かめます。量子化した場合は回答の質の変化も見ます。
  6. 並列数を触っていないか確認する。 OLLAMA_NUM_PARALLEL の既定は1とされています。上げた覚えがあるなら、同時に処理する分のメモリが増えるため、元に戻して測り直します。

最初の遅さが「最初の1回だけ」なら、設定の問題ではなく読み込み待ちの可能性があります。FAQによれば、モデルは既定で5分間メモリに残ります(keep_alive、またはサーバー全体なら OLLAMA_KEEP_ALIVE)。その時間を過ぎると、次の質問で再読み込みが入ります。

測定結果から次の一手を決める判断表

  • load_s が大きく、2回目以降は小さい、疑うこと:読み込み待ち、保持時間切れ、次にやること:keep_alive を長くするか、続けて使う
  • prompt_eval_s が大きい、疑うこと:未キャッシュの入力が多い、入力処理が遅い、次にやること:入力を短くする。同じ質問の反復ではキャッシュの影響にも注意する
  • gen_tokens_per_s が低く、PROCESSORにCPUが混じる、疑うこと:GPUメモリ不足などの可能性、次にやること:手順2→3→4の順で試す
  • gen_tokens_per_s が低く、100% CPU、疑うこと:GPUが使われていない、次にやること:対応GPUを使う予定ならログと環境の確認(手順1)
  • 100% GPU なのに低い、疑うこと:モデルが大きい、他の負荷、次にやること:モデルを小さくする、他のアプリを閉じる
  • 測るたびに値が大きくぶれる、疑うこと:他の処理との競合、次にやること:3回の中央値を使い、重い作業を止めて測る

AIに記録表の読み解きを頼むときの依頼文

測定結果は、AIに整理させることもできます。ただし、AIに渡すのは数字だけにして、判断と設定変更は自分で行います。

以下はローカルAI(Ollama)の速度測定の記録表です。
gen_tokens_per_s が最も改善した変更と、効果がなかった変更を分けてください。
次に試す項目を、記録から言える範囲で1〜2個だけ提案してください。
表にない情報は推測せず、「追加で測りたい項目」として挙げてください。

(ここに記録表を貼る)

PCの型番やモデル名は伏せても構いません。表だけで十分に整理できます。提案された設定は、そのまま適用せず、本記事の順番で一つずつ測り直して確かめてください。

出典・参考資料