LangChainのJSON出力パーサー
LLMからの出力形式は、プロンプトで直接指定する方法がシンプルですが、LLMの出力が安定しない場合がままあると思うので、LangChainには、構造化した出力形式を指定できるパーサー機能があります。
LangChainには、いくつか出力パーサーがありますが、汎用的に使い道がありそうな、Pydantic/JSON 出力パーサーを試してみました。
1.ライブラリほか準備
from langchain.llms import OpenAI
from langchain.output_parsers import PydanticOutputParser
from pydantic import BaseModel, Field, validator
from typing import List
今回の主役は、「PydanticOutputParser」です。
model = OpenAI(model_name="gpt-3.5-turbo", temperature=0)
モデルはgpt-3.5-turboを使いました。
ChatOpenAIを使えと諭されますが、あくまで試食なので…。😓
もちろん公式のサンプルの通り、'text-davinci-003'でよいです。
出力データ構造・バリデーションの定義
# 出力データ構造の定義
SHIKOKU = ('香川県','愛媛県','徳島県','高知県')
class SouvenirInShikoku(BaseModel):
name: str = Field(description="県名")
specialty: List[str] = Field(description="その県の特産品")
# 出力時のデータのバリデーション
@validator('name')
def include_in_shikoku(cls, field):
if field not in SHIKOKU:
raise ValueError("I can only answer for the souvenirs from Shikoku!")
return field
Pydanticの機能を活用するため、BaseModelを継承して、Fieldに必要なJSON形式の変数名と型を定義します。
出力データのバリデーションは@validator以下で適宜行えます。厳密なバリデーションのロジックを書いてもいいし、LLMにふんわりチェックさせるのも面白いかも。
出力パーサー・プロンプトの設定
parser = PydanticOutputParser(pydantic_object=SouvenirInShikoku)
prompt = PromptTemplate(
template="Answer the user query.\n{format_instructions}\n{query}\n",
input_variables=["query"],
partial_variables={"format_instructions": parser.get_format_instructions()}
)
PydanticOutputParserに作成したpydanticの型を指定します。
実行!
ask_query = "高知の特産品を教えて"
_input = prompt.format_prompt(query=ask_query)
output = model(_input.to_string())
parser.parse(output)
みごと利用しやすそうな感じに成形されて出力できました。😀
エラー処理
実際使うときは、モデルを呼ぶところにエラー処理時の例外処理を書いておくと、バリデーション時のエラーを捕まえられると思います。
そのほかの出力パーサー
Enum Output Parser
指定した列挙型(Enum)で出力
シンプルなので、逆にこれを一番使うのかもしれないです。
DatetimeOutputParser()
datetime型に変換して出力
CommaSeparatedListOutputParser
コンマ区切りのリストで出力
感想
Agent周りなどはLangChainが強い印象ですが、好みの問題だと思いますが、出力関係はマイクロソフトの{{guidance}} とかのほうが使いやすいのかも。場面に応じて複数のフレームワークを使っても良い気がします。
おしまい。ありがとうございました。
この記事が気に入ったらサポートをしてみませんか?