LLMのプロンプトエンジニアリング ― GitHub Copilotを生んだ開発者が教える生成AIアプリケーション開発 読書メモ
📒
June 28, 2025
はじめに
プライベートでLLMを使って文章を洗練させる機会が多くなり、そもそも今後のLLMの重要性はおさまるどころか世界を獲る勢いであり、一旦効率的なプロンプトについて学んでおいたほうがいいと思ったので『LLMのプロンプトエンジニアリング ―GitHub Copilotを生んだ開発者が教える生成AIアプリケーション』を買いました。
この本の良さはなんといっても著者が実際に GitHub Copilot の生みの親という権威性!!内容に説得力があります。
また、歴史の外観やLLMの簡単な仕組みみたいな抽象的なことから、超実践的なテクニックまで例をつけて紹介してくれています。
内容は大変勉強になりましたし、今後活かせそうだなと思える技術に溢れていました。
一方で、AI企業各社が出しているプロンプトガイドライン1にしか書かれていない内容もあったりしたので、本書だけでなく自分がよく使用しているLLMモデルに関するガイダンスも読んでおいたほうが良いと思いました。
とはいえ、本書単体でも学ぶことが多かったので一読されるのはとてもおすすめです!
また本書使ったAI作業についての振り返りなどができたらいいなーと思っています。
以下は読書メモです。
Chapter 1: プロンプトエンジニアリングの世界
LLMの本質
- LLMは本質的にテキスト補完エンジン。トレーニング中に提供されるテキストを模倣するだけ
- 「Language models are few-shot learners」:わずかな例(few-shot)を与えるだけで多様な言語タスクを高品質で実行可能
プロンプトエンジニアリングの洗練度レベル
- チャットアプリケーション:会話スレッドをChatML形式のMarkdownでラップ
- モデル入力の修正・拡張:音声活用、別タブ情報参照、ステートフルなやり取り
- API連携:実世界とのつながり、情報読み取り、インターネットアセット作成・変更
- エージェント機能:広範な目標に対して独自判断を下すLLM
Chapter 2: LLMを理解する
基本的な考え方
- プロンプト設計の基本原則:「合理的な人間の反応」ではなく、「このプロンプトで始まるドキュメントがどう続くか」を考える
- トレーニングデータの理解:データを知るほど、LLMの出力について直感を形成しやすくなる
ハルシネーション対策
- ハルシネーション:事実と異なるがもっともらしく見える情報を自信を持って生成する現象
- 「勝手に作り話にしないで」は無意味:モデル視点では他の補完と区別がつかないため
- 効果的な対策:検証可能な背景情報を提供(推測の説明、独立計算可能データ、参照リンク等)
- ハルシネーション誘発の注意:実在しないものに言及すると、LLMは実在すると想定してしまう
トークン化の理解
- トークンvs単語:LLMはテキストをトークン集合として処理、人間は単語集合として認識
3つの重要な違い
- 決定論的トークナイザー:
ghost
→g oh st
に分解。誤字を簡単に見分けられるが、LLMは誤字に強い耐性を持つ - 文字の逐次確認不可:文法的処理(反転など)が困難。対策は「大量リスト生成→ユーザーが絞り込み」
- 大文字小文字の扱い:
gone
(1トークン)vsGONE
(「G」「ONE」の2トークン)
- コンテキストウィンドウ:LLMが一度に扱えるテキスト量の上限(トークン数で制限)
- 多言語の非効率性:英語最適化のため、他言語では1トークンあたり文字数が減少
自己回帰の特性と限界
- 基本動作:複数トークンから次の1トークンを予測
- 不可逆性:一度出力したトークンを覆せない→筋違いな方向に突き進む可能性
- パターンループ:自身が作ったパターンにはまり込んで抜け出せなくなる
Temperature制御
- Temperature:0以上の数値でモデルの「創造性」を制御
- 典型的な値:
- 0:最も有力なトークン選択
- 0.1-0.4:わずかな彩りある回答、少数から最良を選択
- 0.5-0.7:多様性重視、10個の独立回答例など
- 1:トレーニングデータの出現確率を反映
- 1超:「酔っぱらい」状態、奇妙な選択で誤り率増大
Chapter 3: チャット形式への移行
アライメントの重要性
- アライメント:モデルをファインチューニングしてユーザー期待に沿った出力を得るプロセス
- HHH原則:
- Helpful(有用):指示に忠実、簡潔で役立つ回答
- Honest(正直):虚偽情報を作らず、不確実性を明示
- Harmless(無害):差別的偏見や危険情報、攻撃的コンテンツを回避
アライメントのプロセス
- SFT(教師ありファインチューニング):数万件の人手による模範対話データでトレーニング
- 報酬モデル:品質を表す数値スコアを出力、人間の主観的「よさ」を反映
- PPO強化学習:報酬追求の「抜け道」を防ぐ特殊アルゴリズム
- アライメント税:HHHを極めるあまり知能が低下する現象
ChatML(Chat Markup Language)
- 目的:単なる補完ではなく対話・指示従順・質問回答を明確化
- 3つの役割:
system
、user
、assistant
- システムメッセージ:「ルールブック」として活用、メタ情報注入(例:英国紳士風反応)
- 重要な認識:高度機能追加でもLLMの核は「補完エンジン」
Chapter 4: LLMアプリケーションの設計
プロンプトが満たすべき4つの水準
1. 赤ずきんの法則
- 定義:プロンプトはトレーニングセット中のドキュメントに近い形式であるべき
- 要点:トレーニングデータから外れないこと
- 実践:Markdown使用でモデルに理解しやすい形式を提示
2. 必要情報の完全包含
- 必要性:問題解決に必要な情報をすべて含める(旅行計画ならカレンダー情報等)
- 注意点:関連性の低い情報の詰め込みすぎは本筋逸脱の原因
3. 有用な補完生成の条件づけ
- チャットモデル:比較的簡単に実現
- 補完モデル:より慎重な設計が必要
4. 確実な停止機能
- チャットモデル:自然停止
- 補完モデル:stopパラメータ指定、解決達成時の停止期待を明示
重要な概念と手法
RAG(検索拡張生成)
- 目的:モデル未学習情報をプロンプトに追加し新たな知識を提供
- 利点:ハルシネーション防止、最新情報活用
思考の連鎖(CoT)プロンプティング
- 定義:最終回答前に段階的思考プロセスを要求する手法
- 効果:高度な推論パターンの引き出し
適切な文体の使用
- 原則:不適切な文章使用→モデルも雑な文体で生成
- 対策:丁寧で適切な文章でプロンプト作成
Chapter 5: プロンプトのコンテンツ
静的コンテンツ vs 動的コンテンツ
静的コンテンツ
- 定義:常に変わらないもの、タスク伝達・質問整理・手順提示
- 例:「次に読むといい本の提案をお願いします」
- 特徴:ユーザーや状況が変わっても不変
動的コンテンツ
- 定義:その都度変わるもの、質問対象のコンテキスト提供
- 例:「最後に読んだ本は『白鯨』でした」
- 特徴:ユーザーによって変化(白鯨→マクベス→資本論など)
明確化の重要性
- 理由1:LLMでは誤解が完全失敗につながりやすい
- 理由2:一貫したアプローチの実現
- 2つの形態:
- 明示的:「Markdownを使用してください」
- 暗黙的:例示による指導
Few-shotプロンプティング
- 定義:プロンプトに例を追加してパターン認識を促す手法
- 利点:
- 繊細なニュアンスのコントロール可能
- 複雑な指示より扱いやすい
- 暗黙的ルールの学習
3つの欠点
- コンテキストウィンドウ超過:例の過多による制限突破
- アンカリングバイアス:例示情報への過度な偏り
- 誤ったパターン示唆:不適切な例による誤学習
動的コンテンツの特徴
- 待ち時間:実行時の動的収集が必要
- 準備可能性:事前準備の可否
- 比較可能性:情報の有用性評価
チェーホフの銃の誤謬
- 定義:モデルが与えられた情報を必ず活用しようとする傾向
- 問題:完全に無関係なコンテキストも重要と解釈
- 対策:関連性の高い情報のみ提供
階層的要約
- 用途:長文がコンテキストウィンドウに収まらない場合
- 注意点:うわさ話のような誤解の連鎖拡大リスク
Chapter 6: プロンプトの組み立て
基本原則
- 簡潔性:簡潔でわかりやすいプロンプトほど効果的
コンテキスト内学習の特性
- 近接効果:プロンプト末尾に近い情報ほど大きな影響
- 中間部の喪失:冒頭と末尾は思い出しやすいが、中間は活用困難
- 無関心の谷:プロンプト中盤があまり考慮されない現象
対策
- リフォーカス:本題の質問をリマインド
- サンドイッチ手法:再度主題を問いかけ
推奨ドキュメント形式
- 会話形式:人間同士の対話を模したドキュメント構造(RLHFの利点)
- Markdown:一貫した推奨形式、冒頭への注意が有用
- 構造化形式:XML、YAML推奨、JSON非推奨(エスケープ多数で可読性低)
スニペットフォーマット化のポイント
- モジュール性:簡単な挿入/削除
- 自然さ:有機的な文書馴染み
- 簡潔さ:効率的情報伝達
- 独立性:前後への影響回避
プロンプト要素間の関係
- ポジション:要素の並びと場所
- 重要度:情報伝達の重要性
- 依存関係:要素間の相互関係
Chapter 7: モデルの制御
補完構造の制御
序文の3つの種類
- 構造的ボイラープレート:プロンプトと補完の間のテキスト
- 推論:思考の連鎖(CoT)など、モデルが考えるプロセス
- 無意味な要素:RLHFモデルが生成する丁寧だが冗長なテキスト
認識可能な開始と終了
- 重要性:LLMレスポンスから主回答を正確に抽出するため
- 手法:Markdownの見出しや特定の構文を活用
- 停止シーケンス:
stop
引数で特定文字列生成時に停止→コストと待ち時間削減
logprob(対数確率)の詳細活用
3つの主要用途
-
補完品質評価:
- 各トークン選択の信頼度を数値化
- テキスト全体のlogprob合計で「正しさ」の信頼度推定
- 自信がない部分の特定→より良いLLMや追加コンテキストの判断材料
-
分類タスクへの応用:
- LLMを分類に利用
- logprobで分類確実性のキャリブレーション(調整)
-
プロンプト重要ポイントの理解:
echo=true
パラメータでプロンプトのlogprob取得- タイプミスや予期せぬ部分、情報密度の高い部分を検出
モデル選択の基準(重要度順)
- 知能:複雑推論や正確回答の要件
- スピード:待ち時間の許容度
- コスト:推論実行費用
- 使いやすさ:デプロイ、管理の容易さ
- 機能:チャット、ツール利用、logprob、マルチモダリティサポート
- 特別要件:非商用、オープンソース、データ所在地、ロギング等
ファインチューニングの詳細
2つの主要アプローチ
-
完全ファインチューニング/継続的事前トレーニング:
- 全パラメータ調整
- 新しい事実や領域の学習が可能
-
LoRA(低ランク適応):
- パラメータ効率の良いファインチューニング
- 既存テクニックの使い方を教えるのに適している
- より高速で効率的
- 特定スタイルや専門分野特化LLM育成に最適
重要な注意点
- ファインチューニング後は 「赤ずきんの原則」が変化
- プロンプトはファインチューニング用ドキュメントの冒頭に似せるべき
- 元のドキュメントに似ていないように注意
Chapter 8: 会話型エージェント
ツールの概念と実装
ツールの定義方法
- TypeScript関数形式で内部プロンプトに表現
- モデルが正しい型で引数整形
- 一貫した関数呼び出しを実現
ツール設計のベストプラクティス
- キャメルケース命名規則推奨
- 定義の単純化:ただし曖昧性は完全除去
- 詳細説明が必要な場合:モデル混乱を避ける明確性確保
危険なツールの安全対策
- モデル側での制限は不適切
- アプリケーション層で危険リクエスト検知
- 必ずユーザーの明示的承認を取得
- 人間の介入と承認の仕組みを必須実装
高度な推論テクニック
CoT(思考の連鎖)の発展形
- 基本CoT:「段階的に考えよう」で推論生成促進
- Few-shot例との組み合わせ:より思慮深く正確な応答
ReAct(推論とアクション)
- 基本パターン:「思考→アクション→観察」のループ反復
- 適用場面:情報検索と多段階問題解決
- 効果:ファインチューニングモデルが大規模バニラモデルより高品質達成
ReActの5つの思考ステップ
- タスク目標分解、アクションプラン作成
- 常識知識の注入
- 観察からの有用詳細抽出
- 進捗追跡、アクションプラン推進
- 例外処理、アクション方針調整
ReAct超越のアプローチ
- Plan-and-Solve:包括的計画を最初に立案
- Reflexion:事後作業再検討、問題特定、改善計画
- Branch-Solve-Merge:複数LLMで独立解決後マージ
会話型エージェントの構造
- コンテキスト構成:序文、前の会話、現在の取り交わし
- 成果物(Artifacts):会話関連の任意データ(航空券情報、コード等)
- UI要素:処理中スピナー、ツール使用インジケーター、実行詳細の可視化
Chapter 9: LLMワークフロー
基本コンセプト
- 目的:「一般性」vs「強み」のトレードオフで 「強み」を向上
- アプローチ:大タスクを明確定義された小タスクに分割
- 利点:モジュール化で構築容易、問題の原因特定と修正が簡単
ワークフロー構築の5ステップ
1. 目標定義
- 明確で測定可能な目標設定
2. タスク指定
- 適切順序の一連タスクへの分割
- 各タスクの入出力を明確化
- 例:「本の要約作成」→「各章要点抽出」「全体構成生成」「導入部執筆」「結論執筆」
3. タスク実装
- 従来ソフトウェアまたはLLMで実装
- LLMベース実装要素:
- テンプレート化プロンプト使用
- コンテキスト収集・ランク付け・削減
- 構造化出力(JSONスキーマ準拠データ抽出)
- CoTやReActによる推論強化
- 自己修正(リフレクション):過去試行とエラー分析で学習
- 多様な実装選択:ウェブクローラー、従来ML、人間介入、異なるLLM使い分け
4. ワークフロー実装
- バッチワークフロー:既知有限作業項目の一括処理
- ストリーミングワークフロー:リアルタイム継続処理
5. ワークフロー最適化
- 各タスク最適化で品質・パフォーマンス・コスト改善
- オフラインハーネステスト構築で本番前動作確認
高度なLLMワークフロー
- LLMエージェントによるワークフロー駆動:LLM自体がオーケストレーション
- エージェントのエージェント構造
- 役割と委任(AutoGenライブラリ):
- Assistant:ツール装備の会話型エージェント
- UserProxy:人間代役、指示・進捗監視エージェント
Chapter 10: LLMアプリケーションの評価
評価の2つのカテゴリ
オフライン評価
目的:新機能をユーザー提供「前」のテスト
サンプルスイート
- 構成:入力例5-20個、プロンプト生成スクリプト、目視確認
- 用途:迅速な「統制的探査」
サンプル発見方法
- 既存例マイニング:人間が解決した過去記録
- アプリケーション生成:ユーザー使用で蓄積されるデータ
- 合成・創作:LLMに例を生成させる
解決策評価の3アプローチ
-
判断基準(Gold Standard)との一致:
- 既知正解との比較
- 部分一致メトリクス:重要側面のみ比較
-
機能テスト:
- 補完が「機能する」か確認(コードコンパイル、JSONパース等)
-
LLMアセスメント:
- LLM自体に品質評価させる
- 重要注意:第三者採点と思わせるプロンプト設計
- SOMAアセスメント:
- Specific questions(具体的質問)
- Ordinal scale(順序尺度)
- Multiple aspects(複数側面)
- Anchoring(アンカリング)
オンライン評価
目的:実ユーザー利用状況からのフィードバック取得
A/Bテスト
- 2つ以上選択肢を異なるユーザーグループにリリース
- 最高パフォーマンス選択肢の特定
5種類のメトリクス
- 直接フィードバック:Good/Badボタン、アンケート
- 機能の正確性:試行したことの成功度
- ユーザー受け入れ:提案への従順度(クリック率等)
- GitHub Copilot例:コード補完「受け入れ率」が生産性向上と強相関
- 達成された影響:提案の最終的利点(マーケティングメール→販売等)
- 付随的メトリクス:待ち時間、会談時間、エラー率等
評価の重要性
- LLMアプリケーション継続開発に不可欠
- この領域への時間投資は価値が高い
Chapter 11: 未来を見据えて
歴史的視点
- 理解の尺度:人類の歴史は対数スケールでしか理解不可
本書の核心となる教訓
1. LLMの本質理解
- 基本認識:学習時テキスト模倣の単なる補完エンジン
2. LLMへの共感と理解
- 気が散りやすい:無用情報でプロンプト埋めない、全情報に意味を持たせる
- 解読能力の限界:人間が理解できないプロンプトはLLMも混乱
- ガイダンスの必要性:明示的指示提供、適切な例示
- 超能力者ではない:必要情報の提供、ツール・指示の供与が人間の責任
- 内的独り言の不在:声に出して考える(CoT)許可で解決策到達が容易
Footnotes
-
例えばAnthropic の Claudeならこのあたり:Claude 4 プロンプトエンジニアリングのベストプラクティス - Anthropic ↩