一つの judge では足りない
LLM の出力を評価するのに別の LLM を使う「LLM-as-a-Judge」は広く使われています。人手評価と高い相関が出ることが多く、スケールもします。
ただし一種類の judge に頼ると、観測できない側面が出てきます。意味的な正確さ(書いてある内容が事実と合っているか)は LLM judge が得意でも、「文章が十分に具体的か」という定量的な判断はぶれやすい。さらに「特定ドメインで許されない表現か」のような専門的な分類は、汎用 LLM より小さな専用分類器の方が安定することすらあります。
評価したい観点は本来複数あります。それを一つの judge に押し込めず、観点ごとに適した judge を割り当て、束ねるのが現実的な設計です。
共通インターフェースで束ねる
まず器を決めます。すべての judge が同じ形の入力を受け、同じ形の結果を返すようにします。
@dataclass
class JudgeResult:
label: Literal["OK", "NG", "UNCERTAIN"]
confidence: float # 0.0〜1.0
reason: str
class BaseJudge(ABC):
@abstractmethod
async def evaluate(self, ctx: JudgeContext) -> JudgeResult: ...
この器さえ揃えれば、呼び出し側は judge の中身を意識せずに動かせます。「このケースには LLM judge と分類器の両方を走らせ、どちらかが NG なら失敗」という組み合わせも、ループで回すだけになります。以下、三種類を具体的に見ます。
① LLM judge — 意味的な正確さ
LLM に「この出力は入力と矛盾していないか」を判定させます。設計上の勘所が二つあります。
本番のチェックロジックを再利用する。 評価専用のプロンプトを別に書くと、本番でユーザーに見せる品質と、テストで測っている品質がずれていきます。本番の正確性チェック処理をそのまま judge として呼べば、本番とテストが同じ物差しになります。
生成と評価で別モデルを使う。 同じモデルに生成も採点もさせると、モデルが自分の出力に甘い点を付ける preference leakage が起きてスコアが水増しされます。生成と評価のモデルは必ず分けます。
② メトリック judge — 定量的な観点
LLM に判断させるまでもなく、関数で数値化できる観点はメトリック judge に任せます。
class MetricJudge(BaseJudge):
def __init__(self, metric_fn: Callable[[str], float]):
self.metric_fn = metric_fn
async def evaluate(self, ctx: JudgeContext) -> JudgeResult:
score = self.metric_fn(ctx.text)
label = "OK" if score >= 0.5 else "NG"
return JudgeResult(label, confidence=score, reason=f"score={score:.3f}")
「具体性スコア」「文字数の妥当性」「特定キーワードの含有」など、ルールベースで測れるものが対象です。LLM 呼び出しがないので計算コストはほぼゼロ。大量のケースを一次スクリーニングするのに向きます。
③ ドメイン分類器 judge — 専門的な分類
特定ドメインの判定(有害表現の検出など)には、ローカルで動く軽量な分類器を judge にします。
class ClassifierJudge(BaseJudge):
async def evaluate(self, ctx: JudgeContext) -> JudgeResult:
score = self.classifier.classify(ctx.text) # 0.0〜1.0
label = "NG" if score > self.threshold else "OK"
return JudgeResult(label, confidence=score, reason=f"risk={score:.3f}")
本番環境に機械学習ライブラリを載せられない場合でも、評価パイプラインの中でだけ動かせばよいので、Naive Bayes のような軽量モデルを judge として使えます。LLM を呼ばないため、これも大量バッチで遅延しません。
三軸を組み合わせる
三つを同じインターフェースに揃えた効果が、ここで効いてきます。
LLM judge → 内容は事実と整合しているか
メトリック judge → 形式・分量は妥当か
分類器 judge → ドメイン固有のNGに触れていないか
一つの出力をこの三軸で同時に測り、どれか一つでも NG なら不合格、とすれば、単一の judge では取りこぼす側面までカバーできます。観点が増えたら judge を一つ足すだけで、評価の枠組みはそのまま使えます。
まとめ
- 評価したい観点は複数ある。一つの judge に押し込めず、観点ごとに適した judge を割り当てる
- 共通インターフェース(同じ入力・同じ
JudgeResult)で束ねると、組み合わせと差し替えが容易になる - LLM judge: 意味的な正確さ。本番ロジックを再利用し、生成とは別モデルで評価する
- メトリック judge: 関数で測れる定量観点。高速・低コスト
- 分類器 judge: ドメイン特化の軽量モデル。LLM を呼ばず専門判定できる