ChatGPT: なぜ LLM の回答は毎回異なるのか?

質問1

ChatGPT や Gemini などの LLM を使う場合に、同じプロンプトを入力しても回答が毎回異なります。 これは、現在のLLMの実装の仕組み上、仕方がないのでしょうか? それともランダムに回答するような仕組みが入っていますか? 今までのコンピュータのプログラムは、同じ入力には同じ出力が出るのが普通で、ランダムな出力をする方が工夫が必要なことが多いと思います。 このあたりについて詳しく教えてください。

回答

とても良い質問です。整理して説明します。


1. なぜ同じプロンプトでも回答が変わるのか

現在の ChatGPT や Gemini などの LLM では、「確率的に次の単語(トークン)を選ぶ」仕組みを使っています。 つまり、入力に対して最もありそうな単語だけを必ず固定的に選ぶのではなく、確率分布に基づいて複数候補の中から選んでいきます。そのため、同じ入力でも違う出力が生成されることがあります。


2. ランダム性は仕組みとして意図的に入っている

はい。 ランダムに見える挙動は「モデルが確率的に単語をサンプリングしている」ために生じます。これは単なるノイズではなく、多様な表現・自然さを生み出すための仕組みです。もし確率分布の中で常に一番高い確率の単語(greedy decoding)だけを選べば、同じ入力に対しては毎回同じ出力になりますが、以下の問題が出ます:

  • 表現が単調になる
  • 長文では不自然な繰り返しが増える
  • クリエイティブさが欠ける

そのため、通常は temperaturetop_p といったパラメータを使って「確率分布からのランダム抽出」を制御しています。


3. 今までのコンピュータとの違い

おっしゃる通り、従来のプログラムは「同じ入力 → 同じ出力」が基本でした。 LLM も同じ内部状態と同じ乱数シードを固定すれば再現可能ですが、デフォルトでは多様性を持たせるためにランダム性を利用します。

つまり、

  • 通常利用: 毎回少し異なる結果(自然さ・多様性重視)
  • シード固定・温度=0: 毎回同じ結果(再現性重視)

と、用途に応じて切り替え可能です。


4. まとめ

  • LLM の出力は確率的サンプリングにより変動する
  • ランダム性は自然さと多様性のために意図的に導入されている
  • 温度や乱数シードを制御すれば「同じ入力 → 同じ出力」を実現できる

もしご興味があれば、「温度=0 の場合どんな挙動になるか」や「シード固定の方法」を実際のコード例でお見せできますが、見てみますか?

質問2

理解を確認させてください。 「生成AI」と呼ばれるように、文章などを生成することに重き置くために 多様な表現のための機能が入っていると思っていいでしょうか? ビジネスなど、例えばIT開発における品質評価などで利用する際に、 多様な表現がない方が良い場合、シード固定・温度=0 にするのが いいということでしょうか?

回答

はい、その理解で大筋合っています。

  • 生成系タスクでは「自然さ/多様性」を出すために、確率分布からサンプリングする仕組み(= 意図的なランダム性)が入っています。
  • 一方で、業務の品質評価など“常に同じ出力が望ましい”用途では、乱数シードの固定サンプリングの抑制(= 温度を下げる/0にする)再現性を高めるのが定石です。OpenAI も「seed を固定すると(ほぼ)再現可能になる」と公式に案内しています。 (OpenAI Cookbook, Microsoft Learn)

ただし注意点が2つあります。

  1. 温度パラメータ(temperature)の扱い(GPT-5系) GPT-5 の一部エンドポイント/実装では temperature が見えづらかったり効きが弱いという報告があります。とはいえ、多くの GPT-5 ファミリでは依然として temperature を指定でき、0 に近づけるほど決定的に振る舞います(未指定時は既定=1のケースが多い)。挙動はモデルやエンドポイントで差があるため、seed と併用して実測確認するのが安全です。 (OpenAI Community)

  2. 「完全な」決定性ではない 同じ seed とパラメータでも、バックエンド更新やシャーディング差、バージョン差で微妙に変わることがあります(“ほぼ”決定的)。実運用では**モデルのスナップショットを固定(可能なら)**し、system fingerprint の変化やモデル更新日を監視するのがベストプラクティスです。 (OpenAI Cookbook, GitHub)


実装例(Python / Responses API)

ご提示のコードに seed 固定温度 0 を足した最小例です。top_p=1、ペナルティ類は 0 にして、サンプリングの自由度を抑えます。

import os
from openai import OpenAI
from dotenv import load_dotenv

load_dotenv()
client = OpenAI(api_key=os.getenv("OPENAI_API_KEY"))

openai_messages = [{"role": "user", "content": "こんにちは"}]

resp = client.responses.create(
    model="gpt-5-mini",
    input=openai_messages,
    max_output_tokens=1000,
    # 決定性を高めるための設定:
    temperature=0,   # 0 に近いほど“確定的”
    top_p=1,         # サンプル範囲を広げない
    seed=42,         # 乱数シード固定(任意の整数)
    # presence_penalty=0,
    # frequency_penalty=0,
)

print(resp.output_text)

もし temperature が無視される/エラーになる場合

一部の GPT-5 実装で temperature が表に出ていないことがあります。その場合でも seed は効きますtemperature を外してまず seed 固定で再現性を測り、必要に応じて **プロンプトを厳格化(出力フォーマットの固定・手順化)**するのが実務的です。 (OpenAI Cookbook, OpenAI Community)


実務での指針(品質評価・IT 開発など)

  • まず seed 固定(例: 42)
  • 温度は 0 または極小(0〜0.2)
  • top_p=1、各種ペナルティ=0
  • 出力スキーマ/フォーマットを厳格に指定(JSON Schema, “この順序で出力” など)
  • 可能なら モデルのバージョン(スナップショット)を固定し、更新時は再評価する

これで「生成AIの多様性」は抑えつつ、評価や自動テストに使える“安定出力”に寄せられます。必要なら、上の方針でJSON 厳格出力のプロンプト雛形も用意します。