---
title: 法律文件摘要
url: https://platform.claude.com/docs/zh-TW/about-claude/use-case-guides/legal-summarization
description: 本指南將逐步說明如何運用 Claude 先進的自然語言處理能力，有效率地摘要法律文件、擷取關鍵資訊並加速法律研究。透過 Claude，您可以簡化合約審閱、訴訟準備及法規遵循工作，節省時間並確保法律流程的準確性。
---

> 請造訪[摘要 cookbook](https://platform.claude.com/cookbook/capabilities-summarization-guide)，查看使用 Claude 實作法律文件摘要的範例。

## 使用 Claude 建構之前

### 決定是否使用 Claude 進行法律文件摘要

以下是一些關鍵指標，顯示您應該採用像 Claude 這樣的「large language model」（大型語言模型），即 LLM，來摘要法律文件：

<AccordionGroup>
  <Accordion title="您希望以高效率且經濟實惠的方式審閱大量文件">
    大規模的文件審閱若以人工進行，可能既耗時又昂貴。Claude 能夠快速處理並摘要大量法律文件，大幅降低文件審閱所需的時間與成本。這項能力對於盡職調查、合約分析或訴訟證據開示等講求效率的任務特別有價值。
  </Accordion>

  <Accordion title="您需要自動擷取關鍵中繼資料">
    Claude 能夠有效率地從法律文件中擷取並分類重要的中繼資料，例如相關當事人、日期、合約條款或特定條文。這種自動化擷取有助於整理資訊，讓大型文件集更易於搜尋、分析與管理。這對於合約管理、合規檢查或建立可搜尋的法律資訊資料庫特別有用。
  </Accordion>

  <Accordion title="您希望產生清晰、簡潔且標準化的摘要">
    Claude 能夠產生遵循預定格式的結構化摘要，讓法律專業人員更容易快速掌握各類文件的重點。這些標準化摘要可以提升可讀性、便於文件之間的比較，並增進整體理解，尤其是在處理複雜的法律用語或專業術語時。
  </Accordion>

  <Accordion title="您的摘要需要精確的引用">
    在製作法律摘要時，適當的出處標註與引用對於確保可信度及符合法律標準至關重要。您可以透過提示讓 Claude 為所有引用的法律要點附上準確的引用來源，讓法律專業人員更容易審閱並驗證摘要資訊。
  </Accordion>

  <Accordion title="您希望簡化並加速法律研究流程">
    Claude 能夠快速分析大量判例、法規及法律評論，協助進行法律研究。它可以找出相關先例、擷取關鍵法律原則，並摘要複雜的法律論證。這項能力可以大幅加快研究流程，讓法律專業人員能專注於更高層次的分析與策略制定。
  </Accordion>
</AccordionGroup>

### 確定您希望摘要擷取的細節

任何一份文件都沒有唯一正確的摘要。若缺乏明確的指引，Claude 可能難以判斷應納入哪些細節。為了獲得最佳結果，請先確認您希望摘要中包含的具體資訊。

舉例來說，在摘要一份轉租合約時，您可能希望擷取以下重點：

<CodeGroup exclude="shell">
  ```python Python
  details_to_extract = [
      "Parties involved (sublessor, sublessee, and original lessor)",
      "Property details (address, description, and permitted use)",
      "Term and rent (start date, end date, monthly rent, and security deposit)",
      "Responsibilities (utilities, maintenance, and repairs)",
      "Consent and notices (landlord's consent, and notice requirements)",
      "Special provisions (furniture, parking, and subletting restrictions)",
  ]
  ```

  ```typescript TypeScript
  const detailsToExtract = [
    "Parties involved (sublessor, sublessee, and original lessor)",
    "Property details (address, description, and permitted use)",
    "Term and rent (start date, end date, monthly rent, and security deposit)",
    "Responsibilities (utilities, maintenance, and repairs)",
    "Consent and notices (landlord's consent, and notice requirements)",
    "Special provisions (furniture, parking, and subletting restrictions)"
  ];
  ```

  ```csharp C#
  List<string> detailsToExtract =
  [
      "Parties involved (sublessor, sublessee, and original lessor)",
      "Property details (address, description, and permitted use)",
      "Term and rent (start date, end date, monthly rent, and security deposit)",
      "Responsibilities (utilities, maintenance, and repairs)",
      "Consent and notices (landlord's consent, and notice requirements)",
      "Special provisions (furniture, parking, and subletting restrictions)",
  ];
  ```

  ```go Go
  var detailsToExtract = []string{
  	"Parties involved (sublessor, sublessee, and original lessor)",
  	"Property details (address, description, and permitted use)",
  	"Term and rent (start date, end date, monthly rent, and security deposit)",
  	"Responsibilities (utilities, maintenance, and repairs)",
  	"Consent and notices (landlord's consent, and notice requirements)",
  	"Special provisions (furniture, parking, and subletting restrictions)",
  }
  ```

  ```java Java
  List<String> detailsToExtract = List.of(
          "Parties involved (sublessor, sublessee, and original lessor)",
          "Property details (address, description, and permitted use)",
          "Term and rent (start date, end date, monthly rent, and security deposit)",
          "Responsibilities (utilities, maintenance, and repairs)",
          "Consent and notices (landlord's consent, and notice requirements)",
          "Special provisions (furniture, parking, and subletting restrictions)");
  ```

  ```php PHP
  $detailsToExtract = [
      'Parties involved (sublessor, sublessee, and original lessor)',
      'Property details (address, description, and permitted use)',
      'Term and rent (start date, end date, monthly rent, and security deposit)',
      'Responsibilities (utilities, maintenance, and repairs)',
      "Consent and notices (landlord's consent, and notice requirements)",
      'Special provisions (furniture, parking, and subletting restrictions)',
  ];
  ```

  ```ruby Ruby
  details_to_extract = [
    "Parties involved (sublessor, sublessee, and original lessor)",
    "Property details (address, description, and permitted use)",
    "Term and rent (start date, end date, monthly rent, and security deposit)",
    "Responsibilities (utilities, maintenance, and repairs)",
    "Consent and notices (landlord's consent, and notice requirements)",
    "Special provisions (furniture, parking, and subletting restrictions)"
  ]
  ```
</CodeGroup>

### 建立成功標準

評估摘要品質是出了名的困難任務。與許多其他自然語言處理任務不同，摘要的評估往往缺乏明確、客觀的衡量指標。這個過程可能相當主觀，不同的讀者會重視摘要的不同面向。以下是您在評估 Claude 執行法律文件摘要的表現時，可以考慮的標準。

<AccordionGroup>
  <Accordion title="事實正確性">
    摘要應準確呈現文件中的事實、法律概念及重點。
  </Accordion>

  <Accordion title="法律精確性">
    術語以及對法規、判例或規章的引用必須正確，並符合法律標準。
  </Accordion>

  <Accordion title="簡潔性">
    摘要應將法律文件濃縮為其核心要點，同時不遺漏重要細節。
  </Accordion>

  <Accordion title="一致性">
    若摘要多份文件，LLM 應對每份摘要維持一致的結構與方法。
  </Accordion>

  <Accordion title="可讀性">
    文字應清晰易懂。若受眾並非法律專家，摘要中不應包含可能令受眾困惑的法律術語。
  </Accordion>

  <Accordion title="偏見與公正性">
    摘要應以不帶偏見且公正的方式呈現法律論證與立場。
  </Accordion>
</AccordionGroup>

請參閱[建立成功標準](https://platform.claude.com/docs/zh-TW/test-and-evaluate/develop-tests)指南以了解更多資訊。

***

## 如何使用 Claude 摘要法律文件

### 選擇合適的 Claude 模型

在摘要法律文件時，模型準確性極為重要。對於像這樣需要高準確性的使用情境，Claude Opus 5.5 是絕佳的選擇。如果您的文件規模和數量龐大，以致成本開始成為考量，您也可以嘗試使用較小的模型，例如 Claude Haiku 5.5。

為了協助估算這些成本，以下比較了使用 Opus 與 Haiku 模型摘要 1,000 份轉租合約的成本：

* **內容規模**

  * 合約數量：1,000
  * 每份合約字元數：300,000
  * 總字元數：300M

* **預估 token 數**

  * 輸入 token：108M，每份合約約 108,000 個（約每 2.8 個字元 1 個 token，這是兩個模型在本指南範例合約上呈現的比率）
  * 每份摘要的輸出 token，包括以輸出計費的任何思考 token：Claude Opus 5.5 約 6,200 個，Claude Haiku 5.5 約 3,100 個
  * 總輸出 token：Claude Opus 5.5 為 6.2M，Claude Haiku 5.5 為 3.1M

* **Claude Opus 5.5 預估成本**

  * 輸入 token 成本：108 MTok \* $4.00/MTok = $432.00 USD
  * 輸出 token 成本：6.2 MTok \* $20.00/MTok = $124.00 USD
  * 總成本：$432.00 + $124.00 = $556.00 USD

* **Claude Haiku 5.5 預估成本**，以其超過 100,000 個 token 之提示的價格計算

  * 輸入 token 成本：108 MTok \* $0.50/MTok = $54.00 USD
  * 輸出 token 成本：3.1 MTok \* $2.50/MTok = $7.75 USD
  * 總成本：$54.00 + $7.75 = $61.75 USD

<Tip>
  實際成本可能與這些估計不同。這些 token 數來自在本指南的範例合約上執行

  [建構強大的提示](https://platform.claude.com/docs/zh-TW/about-claude/use-case-guides/legal-summarization#build-a-strong-prompt)

  一節中的範例，約 105,000 個輸入 token，而輸出長度會因文件及每次執行而有所不同。此處每份合約是一個約 108,000 個 token 的提示，超過 Claude Haiku 5.5 

  [長提示價格](https://platform.claude.com/docs/zh-TW/about-claude/pricing#long-context-pricing)

  的 100,000 個 token 門檻。提示維持在 100,000 個 token 以內（含）的文件，則改為支付輸入 $0.10/MTok 和輸出 $0.50/MTok。若要查看適用哪種價格，請使用 

  [token 計數](https://platform.claude.com/docs/zh-TW/build-with-claude/token-counting)

  並將 

  `model`

   設為 

  `claude-haiku-5-5`

   來計算您的文件。
</Tip>

### 將文件轉換為 Claude 可處理的格式

在開始摘要文件之前，您需要先準備資料。這包括從 PDF 中擷取文字、清理文字，並確保其已準備好供 Claude 處理。

以下是在一份範例 PDF 上示範此流程：

<CodeGroup exclude="shell">
  <CodeGroupItem language="cURL">
    在程式碼中從 PDF 擷取文字。
  </CodeGroupItem>

  <CodeGroupItem language="CLI">
    在程式碼中從 PDF 擷取文字。
  </CodeGroupItem>

  ```python Python
  from io import BytesIO
  import re

  import pypdf
  import requests


  def get_llm_text(pdf_file):
      reader = pypdf.PdfReader(pdf_file)
      text = "\n".join([page.extract_text() for page in reader.pages])

      # 移除頁碼
      text = re.sub(r"\n\s*\d+\s*\n", "\n", text)

      # 移除多餘的空白
      text = re.sub(r"\s+", " ", text)

      return text


  # 從 GitHub 儲存庫建立完整 URL
  url = "https://raw.githubusercontent.com/anthropics/claude-cookbooks/main/capabilities/summarization/data/Sample Sublease Agreement.pdf"
  url = url.replace(" ", "%20")

  # 將 PDF 檔案下載至記憶體
  response = requests.get(url)

  # 從記憶體載入 PDF
  pdf_file = BytesIO(response.content)

  document_text = get_llm_text(pdf_file)
  print(document_text[:50000])
  ```

  ```typescript TypeScript
  import { PDFParse } from "pdf-parse";

  async function getLlmText(pdfData: Uint8Array): Promise<string> {
    const parser = new PDFParse({ data: pdfData });
    const result = await parser.getText();
    await parser.destroy();
    let text = result.pages.map((page) => page.text).join("\n");

    // 移除頁碼
    text = text.replace(/\n\s*\d+\s*\n/g, "\n");

    // 移除多餘的空白字元
    text = text.replace(/\s+/g, " ");

    return text;
  }

  // 從摘要 cookbook 下載範例轉租協議
  const response = await fetch(
    "https://raw.githubusercontent.com/anthropics/claude-cookbooks/main/capabilities/summarization/data/Sample%20Sublease%20Agreement.pdf"
  );
  const pdfData = new Uint8Array(await response.arrayBuffer());

  const documentText = await getLlmText(pdfData);
  console.log(documentText.slice(0, 50000));
  ```

  ```csharp C#
  using System.Text.RegularExpressions;
  using UglyToad.PdfPig;
  using UglyToad.PdfPig.DocumentLayoutAnalysis.TextExtractor;

  string GetLlmText(byte[] pdfData)
  {
      using var document = PdfDocument.Open(pdfData);
      var text = string.Join("\n", document.GetPages().Select(page => ContentOrderTextExtractor.GetText(page)));

      // 移除頁碼
      text = Regex.Replace(text, @"\n\s*\d+\s*\n", "\n");

      // 移除多餘的空白字元
      text = Regex.Replace(text, @"\s+", " ");

      return text;
  }

  // 從摘要 cookbook 下載範例轉租協議
  using var httpClient = new HttpClient();
  var pdfData = await httpClient.GetByteArrayAsync(
      "https://raw.githubusercontent.com/anthropics/claude-cookbooks/main/capabilities/summarization/data/Sample%20Sublease%20Agreement.pdf"
  );

  var documentText = GetLlmText(pdfData);
  Console.WriteLine(documentText[..Math.Min(50000, documentText.Length)]);
  ```

  ```go Go
  import (
  	"bytes"
  	"io"
  	"net/http"
  	"regexp"

  	"github.com/ledongthuc/pdf"
  )

  // 範例轉租協議的文字內容
  var documentText string

  func getLLMText(pdfData []byte) (string, error) {
  	reader, err := pdf.NewReader(bytes.NewReader(pdfData), int64(len(pdfData)))
  	if err != nil {
  		return "", err
  	}

  	var pages []string
  	for pageIndex := 1; pageIndex <= reader.NumPage(); pageIndex++ {
  		pageText, err := reader.Page(pageIndex).GetPlainText(nil)
  		if err != nil {
  			return "", err
  		}
  		pages = append(pages, pageText)
  	}
  	text := strings.Join(pages, "\n")

  	// 移除頁碼
  	text = regexp.MustCompile(`\n\s*\d+\s*\n`).ReplaceAllString(text, "\n")

  	// 移除多餘的空白
  	text = regexp.MustCompile(`\s+`).ReplaceAllString(text, " ")

  	return text, nil
  }

  // extractDocumentText 會下載範例轉租協議並擷取其文字。
  func extractDocumentText() {
  	// 從摘要 cookbook 下載範例轉租協議
  	response, err := http.Get("https://raw.githubusercontent.com/anthropics/claude-cookbooks/main/capabilities/summarization/data/Sample%20Sublease%20Agreement.pdf")
  	if err != nil {
  		log.Fatal(err)
  	}
  	defer response.Body.Close()

  	pdfData, err := io.ReadAll(response.Body)
  	if err != nil {
  		log.Fatal(err)
  	}

  	documentText, err = getLLMText(pdfData)
  	if err != nil {
  		log.Fatal(err)
  	}
  	fmt.Println(documentText[:min(50000, len(documentText))])
  }
  ```

  ```java Java
  import java.io.IOException;
  import java.net.URI;
  import java.net.http.HttpClient;
  import java.net.http.HttpRequest;
  import java.net.http.HttpResponse;
  import org.apache.pdfbox.Loader;
  import org.apache.pdfbox.pdmodel.PDDocument;
  import org.apache.pdfbox.text.PDFTextStripper;

  // 範例轉租協議的文字內容
  String documentText;

  String getLlmText(byte[] pdfData) throws IOException {
      try (PDDocument document = Loader.loadPDF(pdfData)) {
          String text = new PDFTextStripper().getText(document);

          // 移除頁碼
          text = text.replaceAll("\\n\\s*\\d+\\s*\\n", "\n");

          // 移除多餘的空白
          return text.replaceAll("\\s+", " ");
      }
  }

  void extractDocumentText() throws IOException, InterruptedException {
      // 從摘要 cookbook 下載範例轉租協議
      HttpRequest request = HttpRequest.newBuilder(URI.create(
                      "https://raw.githubusercontent.com/anthropics/claude-cookbooks/main/capabilities/summarization/data/Sample%20Sublease%20Agreement.pdf"))
              .build();
      byte[] pdfData;
      try (HttpClient httpClient = HttpClient.newHttpClient()) {
          pdfData = httpClient.send(request, HttpResponse.BodyHandlers.ofByteArray()).body();
      }

      documentText = getLlmText(pdfData);
      IO.println(documentText.substring(0, Math.min(50000, documentText.length())));
  }
  ```

  ```php PHP
  use Smalot\PdfParser\Parser;

  $getLlmText = function (string $pdfData): string {
      $document = (new Parser())->parseContent($pdfData);
      $text = implode("\n", array_map(fn ($page) => $page->getText(), $document->getPages()));

      // 移除頁碼
      $text = preg_replace('/\n\s*\d+\s*\n/', "\n", $text);

      // 移除多餘的空白字元
      return preg_replace('/\s+/', ' ', $text);
  };

  // 從摘要 cookbook 下載範例轉租協議
  $pdfData = file_get_contents(
      'https://raw.githubusercontent.com/anthropics/claude-cookbooks/main/capabilities/summarization/data/Sample%20Sublease%20Agreement.pdf'
  );

  $documentText = $getLlmText($pdfData);
  echo substr($documentText, 0, 50000) . "\n";
  ```

  ```ruby Ruby
  require "net/http"
  require "pdf-reader"
  require "stringio"

  def get_llm_text(pdf_data)
    reader = PDF::Reader.new(StringIO.new(pdf_data))
    text = reader.pages.map(&:text).join("\n")

    # 移除頁碼
    text = text.gsub(/\n\s*\d+\s*\n/, "\n")

    # 移除多餘的空白
    text.gsub(/\s+/, " ")
  end

  # 從摘要 cookbook 下載範例轉租協議
  pdf_data = Net::HTTP.get(
    URI("https://raw.githubusercontent.com/anthropics/claude-cookbooks/main/capabilities/summarization/data/Sample%20Sublease%20Agreement.pdf")
  )

  document_text = get_llm_text(pdf_data)
  puts document_text[0, 50_000]
  ```
</CodeGroup>

在此範例中，您首先下載[摘要 cookbook](https://platform.claude.com/cookbook/capabilities-summarization-guide) 中所使用的範例轉租合約 PDF。這份合約取自 [sec.gov 網站](https://www.sec.gov/Archives/edgar/data/1045425/000119312507044370/dex1032.htm)上公開的轉租合約。

此範例使用 `pypdf` (typescript: `pdf-parse`; csharp: `PdfPig`; go: `github.com/ledongthuc/pdf`; java: `org.apache.pdfbox:pdfbox`; php: `smalot/pdfparser`; ruby: `pdf-reader`) 函式庫來擷取 PDF 的內容並將其轉換為文字。接著透過移除頁碼和多餘的空白來清理文字資料。

### 建構強大的提示

Claude 能夠適應各種摘要風格。您可以調整提示的細節，引導 Claude 更詳盡或更精簡、納入更多或更少的專業術語，或針對當前內容提供較高層次或較低層次的摘要。

以下範例說明如何建立一個提示，確保在分析轉租合約時所產生的摘要遵循一致的結構：

<CodeGroup exclude="shell">
  <CodeGroupItem language="cURL">
    此工作流程需要的邏輯超出單一 shell 指令所能處理的範圍。請使用 Claude SDK 來執行。
  </CodeGroupItem>

  <CodeGroupItem language="CLI">
    此工作流程需要的邏輯超出單一 shell 指令所能處理的範圍。請使用 Claude SDK 來執行。
  </CodeGroupItem>

  ```python Python
  # 初始化 Anthropic 用戶端
  client = anthropic.Anthropic()


  def summarize_document(
      text, details_to_extract, model="claude-opus-5-5", max_tokens=16000
  ):
      # 格式化要擷取的細節，以放入提示的上下文中
      details_to_extract_str = "\n".join(details_to_extract)

      # 提示模型摘要轉租合約
      prompt = f"""Summarize the following sublease agreement. Focus on these key aspects:

      {details_to_extract_str}

      Provide the summary in bullet points nested within the XML header for each section. For example:

      <parties involved>
      - Sublessor: [Name]
      // Add more details as needed
      </parties involved>

      If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.

      Sublease agreement text:
      {text}
      """

      response = client.messages.create(
          model=model,
          max_tokens=max_tokens,
          system="You are a legal analyst specializing in real estate law, known for highly accurate and detailed summaries of sublease agreements.",
          messages=[
              {"role": "user", "content": prompt},
          ],
      )

      return next(block.text for block in response.content if block.type == "text")


  sublease_summary = summarize_document(document_text, details_to_extract)
  print(sublease_summary)
  ```

  ```typescript TypeScript
  // 初始化 Anthropic 用戶端
  const client = new Anthropic();

  async function summarizeDocument(
    text: string,
    detailsToExtract: string[],
    model: Anthropic.Model = "claude-opus-5-5",
    maxTokens = 16000
  ): Promise<string> {
    // 格式化要擷取的細節，以放入提示的上下文中
    const detailsToExtractStr = detailsToExtract.join("\n");

    // 提示模型摘要轉租協議
    const prompt = `Summarize the following sublease agreement. Focus on these key aspects:

      ${detailsToExtractStr}

      Provide the summary in bullet points nested within the XML header for each section. For example:

      <parties involved>
      - Sublessor: [Name]
      // Add more details as needed
      </parties involved>

      If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.

      Sublease agreement text:
      ${text}
      `;

    const response = await client.messages.create({
      model,
      max_tokens: maxTokens,
      system:
        "You are a legal analyst specializing in real estate law, known for highly accurate and detailed summaries of sublease agreements.",
      messages: [{ role: "user", content: prompt }]
    });

    const textBlock = response.content.find((block) => block.type === "text");
    if (!textBlock) {
      throw new Error("Expected a text block in the response");
    }
    return textBlock.text;
  }

  const subleaseSummary = await summarizeDocument(documentText, detailsToExtract);
  console.log(subleaseSummary);
  ```

  ```csharp C#
  // 初始化 Anthropic 用戶端
  var client = new AnthropicClient();

  async Task<string> SummarizeDocument(
      string text,
      IReadOnlyList<string> detailsToExtract,
      Model model = Model.ClaudeOpus5_5,
      long maxTokens = 16000
  )
  {
      // 格式化要擷取的細節，以放入提示的上下文中
      var detailsToExtractStr = string.Join("\n", detailsToExtract);

      // 提示模型摘要轉租協議
      var prompt = $"""
          Summarize the following sublease agreement. Focus on these key aspects:

              {detailsToExtractStr}

              Provide the summary in bullet points nested within the XML header for each section. For example:

              <parties involved>
              - Sublessor: [Name]
              // Add more details as needed
              </parties involved>

              If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.

              Sublease agreement text:
              {text}
          """;

      var response = await client.Messages.Create(
          new()
          {
              Model = model,
              MaxTokens = maxTokens,
              System = "You are a legal analyst specializing in real estate law, known for highly accurate and detailed summaries of sublease agreements.",
              Messages = [new() { Role = Role.User, Content = prompt }],
          }
      );

      foreach (var block in response.Content)
      {
          if (block.TryPickText(out var textBlock))
          {
              return textBlock.Text;
          }
      }
      throw new InvalidOperationException("Expected a text block in the response.");
  }

  var subleaseSummary = await SummarizeDocument(documentText, detailsToExtract);
  Console.WriteLine(subleaseSummary);
  ```

  ```go Go
  // 初始化 Anthropic 用戶端
  var client = anthropic.NewClient()

  func summarizeDocument(text string, detailsToExtract []string, model anthropic.Model, maxTokens int64) string {
  	// 格式化要擷取的細節，以放入提示的上下文中
  	detailsToExtractStr := strings.Join(detailsToExtract, "\n")

  	// 提示模型摘要轉租協議
  	prompt := fmt.Sprintf(`Summarize the following sublease agreement. Focus on these key aspects:

      %s

      Provide the summary in bullet points nested within the XML header for each section. For example:

      <parties involved>
      - Sublessor: [Name]
      // Add more details as needed
      </parties involved>

      If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.

      Sublease agreement text:
      %s
      `, detailsToExtractStr, text)

  	response, err := client.Messages.New(context.Background(), anthropic.MessageNewParams{
  		Model:     model,
  		MaxTokens: maxTokens,
  		System: []anthropic.TextBlockParam{
  			{Text: "You are a legal analyst specializing in real estate law, known for highly accurate and detailed summaries of sublease agreements."},
  		},
  		Messages: []anthropic.MessageParam{
  			anthropic.NewUserMessage(anthropic.NewTextBlock(prompt)),
  		},
  	})
  	if err != nil {
  		log.Fatal(err)
  	}

  	for _, block := range response.Content {
  		if textBlock, ok := block.AsAny().(anthropic.TextBlock); ok {
  			return textBlock.Text
  		}
  	}
  	panic("expected a text block in the response")
  }

  // printSubleaseSummary 會摘要轉租協議並印出摘要。
  func printSubleaseSummary() {
  	subleaseSummary := summarizeDocument(documentText, detailsToExtract, anthropic.ModelClaudeOpus5_5, 16000)
  	fmt.Println(subleaseSummary)
  }
  ```

  ```java Java
  // 初始化 Anthropic 用戶端
  AnthropicClient client = AnthropicOkHttpClient.fromEnv();

  String summarizeDocument(String text, List<String> detailsToExtract, Model model, long maxTokens) {
      // 格式化要擷取的細節，以放入提示的上下文中
      String detailsToExtractStr = String.join("\n", detailsToExtract);

      // 提示模型摘要轉租協議
      String prompt = """
              Summarize the following sublease agreement. Focus on these key aspects:

                  %s

                  Provide the summary in bullet points nested within the XML header for each section. For example:

                  <parties involved>
                  - Sublessor: [Name]
                  // Add more details as needed
                  </parties involved>

                  If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.

                  Sublease agreement text:
                  %s
              """
              .formatted(detailsToExtractStr, text);

      Message response = client.messages().create(MessageCreateParams.builder()
              .model(model)
              .maxTokens(maxTokens)
              .system("You are a legal analyst specializing in real estate law, known for highly accurate and detailed summaries of sublease agreements.")
              .addUserMessage(prompt)
              .build());

      return response.content().stream()
              .flatMap(block -> block.text().stream())
              .findFirst()
              .orElseThrow()
              .text();
  }

  void printSubleaseSummary() {
      String subleaseSummary = summarizeDocument(
              documentText, detailsToExtract, Model.CLAUDE_OPUS_5_5, 16000);
      IO.println(subleaseSummary);
  }
  ```

  ```php PHP
  // 初始化 Anthropic 用戶端
  $client = new Client();

  $summarizeDocument = function (
      string $text,
      array $detailsToExtract,
      Model $model = Model::CLAUDE_OPUS_5_5,
      int $maxTokens = 16000,
  ) use ($client): string {
      // 格式化要擷取的細節，以放入提示的上下文中
      $detailsToExtractStr = implode("\n", $detailsToExtract);

      // 提示模型摘要轉租協議
      $prompt = <<<PROMPT
          Summarize the following sublease agreement. Focus on these key aspects:

              {$detailsToExtractStr}

              Provide the summary in bullet points nested within the XML header for each section. For example:

              <parties involved>
              - Sublessor: [Name]
              // Add more details as needed
              </parties involved>

              If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.

              Sublease agreement text:
              {$text}
          PROMPT;

      $response = $client->messages->create(
          model: $model,
          maxTokens: $maxTokens,
          system: 'You are a legal analyst specializing in real estate law, known for highly accurate and detailed summaries of sublease agreements.',
          messages: [['role' => 'user', 'content' => $prompt]],
      );

      $textBlock = array_find($response->content, fn ($block) => $block instanceof \Anthropic\Messages\TextBlock)
          ?? throw new \RuntimeException('Expected a text block in the response.');

      return $textBlock->text;
  };

  $subleaseSummary = $summarizeDocument($documentText, $detailsToExtract);
  echo $subleaseSummary . "\n";
  ```

  ```ruby Ruby
  # 初始化 Anthropic 用戶端
  CLIENT = Anthropic::Client.new

  def summarize_document(text, details_to_extract, model: Anthropic::Model::CLAUDE_OPUS_5_5, max_tokens: 16_000)
    # 格式化要擷取的細節，以放入提示的上下文中
    details_to_extract_str = details_to_extract.join("\n")

    # 提示模型摘要轉租協議
    prompt = <<~PROMPT
      Summarize the following sublease agreement. Focus on these key aspects:

          #{details_to_extract_str}

          Provide the summary in bullet points nested within the XML header for each section. For example:

          <parties involved>
          - Sublessor: [Name]
          // Add more details as needed
          </parties involved>

          If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.

          Sublease agreement text:
          #{text}
    PROMPT

    response = CLIENT.messages.create(
      model:,
      max_tokens:,
      system_: "You are a legal analyst specializing in real estate law, known for highly accurate and detailed summaries of sublease agreements.",
      messages: [{role: :user, content: prompt}]
    )

    response.content.find { |block| block.is_a?(Anthropic::Models::TextBlock) }.text
  end

  sublease_summary = summarize_document(document_text, details_to_extract)
  puts sublease_summary
  ```
</CodeGroup>

此程式碼實作了一個 `summarize_document` (typescript, go, java: `summarizeDocument`; php: `$summarizeDocument`; csharp: `SummarizeDocument`) 函式，使用 Claude 來摘要轉租合約的內容。此函式接受一個文字字串和一份要擷取的細節清單作為輸入。在此範例中，程式碼以先前程式碼片段中定義的 `document_text` (typescript, go, java, csharp: `documentText`; php: `$documentText`) 和 `details_to_extract` (typescript, go, java, csharp: `detailsToExtract`; php: `$detailsToExtract`) 變數呼叫此函式。

在函式內部，會為 Claude 產生一個提示，其中包含要摘要的文件、要擷取的細節，以及摘要文件的具體指示。該提示指示 Claude 以巢狀於 XML 標頭內的方式，回覆每項待擷取細節的摘要。

由於程式碼將摘要的每個區段輸出於標籤之內，因此每個區段都可以在後處理步驟中輕鬆解析出來。這種方法能夠產生可依您的使用情境調整的結構化摘要，讓每份摘要都遵循相同的模式。

### 評估您的提示

提示通常需要經過測試與最佳化，才能達到可投入生產環境的程度。為了判斷您的解決方案是否已準備就緒，請使用結合量化與質化方法的系統化流程來評估摘要品質。根據您所定義的成功標準建立[強大的實證評估](https://platform.claude.com/docs/zh-TW/test-and-evaluate/develop-tests#build-evaluations)，能讓您最佳化提示。以下是您可能希望納入實證評估中的一些指標：

<AccordionGroup>
  <Accordion title="ROUGE 分數">
    此指標衡量所產生的摘要與專家撰寫的參考摘要之間的重疊程度。此指標主要著重於召回率，適合用於評估內容涵蓋範圍。
  </Accordion>

  <Accordion title="BLEU 分數">
    雖然此指標最初是為機器翻譯所開發，但也可調整應用於摘要任務。BLEU 分數衡量所產生的摘要與參考摘要之間 n-gram 比對的精確率。分數越高，表示所產生的摘要包含與參考摘要相似的詞句與術語。
  </Accordion>

  <Accordion title="上下文嵌入相似度">
    此指標需要為所產生的摘要與參考摘要分別建立向量表示（嵌入）。接著計算這些嵌入之間的相似度，通常使用餘弦相似度。相似度分數越高，表示所產生的摘要即使確切用詞不同，仍捕捉到了參考摘要的語意與上下文。
  </Accordion>

  <Accordion title="基於 LLM 的評分">
    此方法使用像 Claude 這樣的 LLM，依據評分標準來評估所產生摘要的品質。評分標準可依您的特定需求量身打造，評估準確性、完整性與連貫性等關鍵因素。如需實作指引，請參閱

    [基於 LLM 評分的技巧](https://platform.claude.com/docs/zh-TW/test-and-evaluate/develop-tests#tips-for-llm-based-grading)

    。
  </Accordion>

  <Accordion title="人工評估">
    除了撰寫參考摘要之外，法律專家也可以評估所產生摘要的品質。雖然大規模進行既昂貴又耗時，但在部署至生產環境之前，通常會針對少數摘要進行此項評估作為驗證檢查。
  </Accordion>
</AccordionGroup>

### 部署您的提示

以下是您將解決方案部署至生產環境時需要留意的一些額外考量。

1. **確保無法律責任：** 了解摘要中的錯誤可能帶來的法律影響，這些錯誤可能導致您的組織或客戶承擔法律責任。請提供免責聲明或法律告示，說明摘要由 AI 產生，應由法律專業人員審閱。

2. **處理多樣的文件類型：** 本指南討論了如何從 PDF 中擷取文字。在實務上，文件可能以各種格式出現（例如 PDF、Word 文件及文字檔）。請確保您的資料擷取管線能夠轉換您預期會收到的所有檔案格式。

3. **平行化對 Claude 的 API 呼叫：** 包含大量 token 的長篇文件可能需要長達一分鐘的時間讓 Claude 產生摘要。對於大型文件集，您可能希望以平行方式向 Claude 發送 API 呼叫，以便在合理的時間內完成摘要。請參閱 Anthropic 的[速率限制](https://platform.claude.com/docs/zh-TW/api/rate-limits#rate-limits)（rate limit），以確定可平行執行的 API 呼叫數量上限。

***

## 提升效能

在複雜的情境中，除了標準的[提示工程技巧](https://platform.claude.com/docs/zh-TW/build-with-claude/prompt-engineering/overview)之外，考慮其他策略來提升效能可能會有所幫助。以下是一些進階策略：

### 執行後設摘要以摘要長篇文件

法律文件摘要經常需要一次處理長篇文件或許多相關文件，以致超出 Claude 的「context window」（上下文視窗）。您可以使用一種稱為後設摘要（meta-summarization）的分塊方法來處理此使用情境。此技術將文件拆分為較小、易於管理的區塊，然後分別處理每個區塊。接著，您可以將各區塊的摘要合併，建立整份文件的後設摘要。

以下是執行後設摘要的範例：

<CodeGroup exclude="shell">
  <CodeGroupItem language="cURL">
    此工作流程需要的邏輯超出單一 shell 指令所能處理的範圍。請使用 Claude SDK 來執行。
  </CodeGroupItem>

  <CodeGroupItem language="CLI">
    此工作流程需要的邏輯超出單一 shell 指令所能處理的範圍。請使用 Claude SDK 來執行。
  </CodeGroupItem>

  ```python Python
  def chunk_text(text, chunk_size=20000):
      return [text[i : i + chunk_size] for i in range(0, len(text), chunk_size)]


  def summarize_long_document(
      text, details_to_extract, model="claude-opus-5-5", max_tokens=16000
  ):
      # 格式化要擷取的細節，以放入提示的上下文中
      details_to_extract_str = "\n".join(details_to_extract)

      # 逐一處理各區塊並分別摘要
      chunk_summaries = [
          summarize_document(
              chunk, details_to_extract, model=model, max_tokens=max_tokens
          )
          for chunk in chunk_text(text)
      ]

      final_summary_prompt = f"""

      You are looking at the chunked summaries of multiple documents that are all related.
      Combine the following summaries of the document from different truthful sources into a coherent overall summary:

      <chunked_summaries>
      {"".join(chunk_summaries)}
      </chunked_summaries>

      Focus on these key aspects:
      {details_to_extract_str}

      Provide the summary in bullet points nested within the XML header for each section. For example:

      <parties involved>
      - Sublessor: [Name]
      // Add more details as needed
      </parties involved>

      If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.
      """

      response = client.messages.create(
          model=model,
          max_tokens=max_tokens,
          system="You are a legal expert that summarizes notes on one document.",
          messages=[
              {"role": "user", "content": final_summary_prompt},
          ],
      )

      return next(block.text for block in response.content if block.type == "text")


  long_summary = summarize_long_document(document_text, details_to_extract)
  print(long_summary)
  ```

  ```typescript TypeScript
  function chunkText(text: string, chunkSize = 20000): string[] {
    return Array.from({ length: Math.ceil(text.length / chunkSize) }, (_, index) =>
      text.slice(index * chunkSize, (index + 1) * chunkSize)
    );
  }

  async function summarizeLongDocument(
    text: string,
    detailsToExtract: string[],
    model: Anthropic.Model = "claude-opus-5-5",
    maxTokens = 16000
  ): Promise<string> {
    // 格式化要擷取的細節，以放入提示的上下文中
    const detailsToExtractStr = detailsToExtract.join("\n");

    // 逐一處理各區塊並分別摘要
    const chunkSummaries: string[] = [];
    for (const chunk of chunkText(text)) {
      chunkSummaries.push(await summarizeDocument(chunk, detailsToExtract, model, maxTokens));
    }

    const finalSummaryPrompt = `

      You are looking at the chunked summaries of multiple documents that are all related.
      Combine the following summaries of the document from different truthful sources into a coherent overall summary:

      <chunked_summaries>
      ${chunkSummaries.join("")}
      </chunked_summaries>

      Focus on these key aspects:
      ${detailsToExtractStr}

      Provide the summary in bullet points nested within the XML header for each section. For example:

      <parties involved>
      - Sublessor: [Name]
      // Add more details as needed
      </parties involved>

      If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.
      `;

    const response = await client.messages.create({
      model,
      max_tokens: maxTokens,
      system: "You are a legal expert that summarizes notes on one document.",
      messages: [{ role: "user", content: finalSummaryPrompt }]
    });

    const textBlock = response.content.find((block) => block.type === "text");
    if (!textBlock) {
      throw new Error("Expected a text block in the response");
    }
    return textBlock.text;
  }

  const longSummary = await summarizeLongDocument(documentText, detailsToExtract);
  console.log(longSummary);
  ```

  ```csharp C#
  IEnumerable<string> ChunkText(string text, int chunkSize = 20000) =>
      text.Chunk(chunkSize).Select(chars => new string(chars));

  async Task<string> SummarizeLongDocument(
      string text,
      IReadOnlyList<string> detailsToExtract,
      Model model = Model.ClaudeOpus5_5,
      long maxTokens = 16000
  )
  {
      // 格式化要擷取的細節，以放入提示的上下文中
      var detailsToExtractStr = string.Join("\n", detailsToExtract);

      // 逐一處理各區塊並分別摘要
      List<string> chunkSummaries = [];
      foreach (var chunk in ChunkText(text))
      {
          chunkSummaries.Add(await SummarizeDocument(chunk, detailsToExtract, model, maxTokens));
      }

      var finalSummaryPrompt = $"""

              You are looking at the chunked summaries of multiple documents that are all related.
              Combine the following summaries of the document from different truthful sources into a coherent overall summary:

              <chunked_summaries>
              {string.Concat(chunkSummaries)}
              </chunked_summaries>

              Focus on these key aspects:
              {detailsToExtractStr}

              Provide the summary in bullet points nested within the XML header for each section. For example:

              <parties involved>
              - Sublessor: [Name]
              // Add more details as needed
              </parties involved>

              If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.
          """;

      var response = await client.Messages.Create(
          new()
          {
              Model = model,
              MaxTokens = maxTokens,
              System = "You are a legal expert that summarizes notes on one document.",
              Messages = [new() { Role = Role.User, Content = finalSummaryPrompt }],
          }
      );

      foreach (var block in response.Content)
      {
          if (block.TryPickText(out var textBlock))
          {
              return textBlock.Text;
          }
      }
      throw new InvalidOperationException("Expected a text block in the response.");
  }

  var longSummary = await SummarizeLongDocument(documentText, detailsToExtract);
  Console.WriteLine(longSummary);
  ```

  ```go Go
  func chunkText(text string, chunkSize int) []string {
  	var chunks []string
  	for chunk := range slices.Chunk([]rune(text), chunkSize) {
  		chunks = append(chunks, string(chunk))
  	}
  	return chunks
  }

  func summarizeLongDocument(text string, detailsToExtract []string, model anthropic.Model, maxTokens int64) string {
  	// 格式化要擷取的細節，以放入提示的上下文中
  	detailsToExtractStr := strings.Join(detailsToExtract, "\n")

  	// 逐一處理各區塊並分別摘要
  	var chunkSummaries []string
  	for _, chunk := range chunkText(text, 20000) {
  		chunkSummaries = append(chunkSummaries, summarizeDocument(chunk, detailsToExtract, model, maxTokens))
  	}

  	finalSummaryPrompt := fmt.Sprintf(`

      You are looking at the chunked summaries of multiple documents that are all related.
      Combine the following summaries of the document from different truthful sources into a coherent overall summary:

      <chunked_summaries>
      %s
      </chunked_summaries>

      Focus on these key aspects:
      %s

      Provide the summary in bullet points nested within the XML header for each section. For example:

      <parties involved>
      - Sublessor: [Name]
      // Add more details as needed
      </parties involved>

      If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.
      `, strings.Join(chunkSummaries, ""), detailsToExtractStr)

  	response, err := client.Messages.New(context.Background(), anthropic.MessageNewParams{
  		Model:     model,
  		MaxTokens: maxTokens,
  		System: []anthropic.TextBlockParam{
  			{Text: "You are a legal expert that summarizes notes on one document."},
  		},
  		Messages: []anthropic.MessageParam{
  			anthropic.NewUserMessage(anthropic.NewTextBlock(finalSummaryPrompt)),
  		},
  	})
  	if err != nil {
  		log.Fatal(err)
  	}

  	for _, block := range response.Content {
  		if textBlock, ok := block.AsAny().(anthropic.TextBlock); ok {
  			return textBlock.Text
  		}
  	}
  	panic("expected a text block in the response")
  }

  // printLongSummary 會逐區塊摘要轉租協議，並印出合併後的摘要。
  func printLongSummary() {
  	longSummary := summarizeLongDocument(documentText, detailsToExtract, anthropic.ModelClaudeOpus5_5, 16000)
  	fmt.Println(longSummary)
  }
  ```

  ```java Java
  List<String> chunkText(String text, int chunkSize) {
      return IntStream.iterate(0, start -> start < text.length(), start -> start + chunkSize)
              .mapToObj(start -> text.substring(start, Math.min(start + chunkSize, text.length())))
              .toList();
  }

  String summarizeLongDocument(String text, List<String> detailsToExtract, Model model, long maxTokens) {
      // 格式化要擷取的細節，以放入提示的上下文中
      String detailsToExtractStr = String.join("\n", detailsToExtract);

      // 逐一處理各區塊並分別摘要
      String chunkSummaries = chunkText(text, 20000).stream()
              .map(chunk -> summarizeDocument(chunk, detailsToExtract, model, maxTokens))
              .collect(Collectors.joining());

      String finalSummaryPrompt = """

                  You are looking at the chunked summaries of multiple documents that are all related.
                  Combine the following summaries of the document from different truthful sources into a coherent overall summary:

                  <chunked_summaries>
                  %s
                  </chunked_summaries>

                  Focus on these key aspects:
                  %s

                  Provide the summary in bullet points nested within the XML header for each section. For example:

                  <parties involved>
                  - Sublessor: [Name]
                  // Add more details as needed
                  </parties involved>

                  If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.
              """
              .formatted(chunkSummaries, detailsToExtractStr);

      Message response = client.messages().create(MessageCreateParams.builder()
              .model(model)
              .maxTokens(maxTokens)
              .system("You are a legal expert that summarizes notes on one document.")
              .addUserMessage(finalSummaryPrompt)
              .build());

      return response.content().stream()
              .flatMap(block -> block.text().stream())
              .findFirst()
              .orElseThrow()
              .text();
  }

  void printLongSummary() {
      String longSummary = summarizeLongDocument(
              documentText, detailsToExtract, Model.CLAUDE_OPUS_5_5, 16000);
      IO.println(longSummary);
  }
  ```

  ```php PHP
  $chunkText = fn (string $text, int $chunkSize = 20000): array => mb_str_split($text, $chunkSize);

  $summarizeLongDocument = function (
      string $text,
      array $detailsToExtract,
      Model $model = Model::CLAUDE_OPUS_5_5,
      int $maxTokens = 16000,
  ) use ($client, $chunkText, $summarizeDocument): string {
      // 格式化要擷取的細節，以放入提示的上下文中
      $detailsToExtractStr = implode("\n", $detailsToExtract);

      // 逐一處理各區塊並分別摘要
      $chunkSummaries = array_map(
          fn (string $chunk) => $summarizeDocument($chunk, $detailsToExtract, $model, $maxTokens),
          $chunkText($text),
      );
      $chunkSummariesStr = implode('', $chunkSummaries);

      $finalSummaryPrompt = <<<PROMPT

              You are looking at the chunked summaries of multiple documents that are all related.
              Combine the following summaries of the document from different truthful sources into a coherent overall summary:

              <chunked_summaries>
              {$chunkSummariesStr}
              </chunked_summaries>

              Focus on these key aspects:
              {$detailsToExtractStr}

              Provide the summary in bullet points nested within the XML header for each section. For example:

              <parties involved>
              - Sublessor: [Name]
              // Add more details as needed
              </parties involved>

              If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.
          PROMPT;

      $response = $client->messages->create(
          model: $model,
          maxTokens: $maxTokens,
          system: 'You are a legal expert that summarizes notes on one document.',
          messages: [['role' => 'user', 'content' => $finalSummaryPrompt]],
      );

      $textBlock = array_find($response->content, fn ($block) => $block instanceof \Anthropic\Messages\TextBlock)
          ?? throw new \RuntimeException('Expected a text block in the response.');

      return $textBlock->text;
  };

  $longSummary = $summarizeLongDocument($documentText, $detailsToExtract);
  echo $longSummary . "\n";
  ```

  ```ruby Ruby
  def chunk_text(text, chunk_size: 20_000)
    text.chars.each_slice(chunk_size).map(&:join)
  end

  def summarize_long_document(text, details_to_extract, model: Anthropic::Model::CLAUDE_OPUS_5_5, max_tokens: 16_000)
    # 格式化要擷取的細節，以放入提示的上下文中
    details_to_extract_str = details_to_extract.join("\n")

    # 逐一處理各區塊並分別摘要
    chunk_summaries = chunk_text(text).map do |chunk|
      summarize_document(chunk, details_to_extract, model:, max_tokens:)
    end

    final_summary_prompt = <<~PROMPT

          You are looking at the chunked summaries of multiple documents that are all related.
          Combine the following summaries of the document from different truthful sources into a coherent overall summary:

          <chunked_summaries>
          #{chunk_summaries.join}
          </chunked_summaries>

          Focus on these key aspects:
          #{details_to_extract_str}

          Provide the summary in bullet points nested within the XML header for each section. For example:

          <parties involved>
          - Sublessor: [Name]
          // Add more details as needed
          </parties involved>

          If any information is not explicitly stated in the document, note it as "Not specified". Do not preamble.
    PROMPT

    response = CLIENT.messages.create(
      model:,
      max_tokens:,
      system_: "You are a legal expert that summarizes notes on one document.",
      messages: [{role: :user, content: final_summary_prompt}]
    )

    response.content.find { |block| block.is_a?(Anthropic::Models::TextBlock) }.text
  end

  long_summary = summarize_long_document(document_text, details_to_extract)
  puts long_summary
  ```
</CodeGroup>

`summarize_long_document` (typescript, go, java: `summarizeLongDocument`; php: `$summarizeLongDocument`; csharp: `SummarizeLongDocument`) 函式建立在先前的 `summarize_document` (typescript, go, java: `summarizeDocument`; php: `$summarizeDocument`; csharp: `SummarizeDocument`) 函式之上，將文件拆分為較小的區塊，並個別摘要每個區塊。

程式碼透過將 `summarize_document` (typescript, go, java: `summarizeDocument`; php: `$summarizeDocument`; csharp: `SummarizeDocument`) 函式套用至原始文件中每個 20,000 字元的區塊來達成此目的。接著合併各個摘要，並從這些區塊摘要建立最終摘要。

請注意，對於範例 PDF 而言，`summarize_long_document` (typescript, go, java: `summarizeLongDocument`; php: `$summarizeLongDocument`; csharp: `SummarizeLongDocument`) 函式並非絕對必要，因為整份文件都能容納在 Claude 的上下文視窗內。然而，對於超出 Claude 上下文視窗的文件，或在一起摘要多份相關文件時，它就變得不可或缺。無論如何，這種後設摘要技術通常能在最終摘要中捕捉到先前單一摘要方法所遺漏的其他重要細節。

### 使用摘要索引文件來探索大型文件集

使用 LLM 搜尋文件集通常涉及「retrieval-augmented generation」（檢索增強生成），即 RAG。然而，在涉及大型文件或精確資訊檢索至關重要的情境中，基本的 RAG 方法可能不夠充分。摘要索引文件（summary indexed documents）是一種進階的 RAG 方法，提供更有效率的文件檢索排序方式，且比傳統 RAG 方法使用更少的上下文。在此方法中，您首先使用 Claude 為語料庫中的每份文件產生簡潔的摘要，然後使用 Claude 對每份摘要與所提問題的相關性進行排序。如需此方法的進一步細節（包括程式碼範例），請查看[摘要 cookbook](https://platform.claude.com/cookbook/capabilities-summarization-guide) 中的摘要索引文件章節。

### 微調 Claude 以從您的資料集中學習

另一項提升 Claude 產生摘要能力的進階技術是「fine-tuning」（微調）。微調是以專門符合您法律文件摘要需求的自訂資料集來訓練 Claude，確保 Claude 能適應您的使用情境。以下是執行微調的概述：

1. **找出錯誤：** 首先收集 Claude 摘要表現不佳的案例——這可能包括遺漏關鍵法律細節、誤解上下文，或使用不恰當的法律術語。

2. **整理資料集：** 一旦找出這些問題，請將這些有問題的範例彙整成資料集。此資料集應包含原始法律文件以及您修正後的摘要，以確保 Claude 學習到期望的行為。

3. **執行微調：** 微調是以您整理的資料集重新訓練模型，以調整其權重與參數。這種重新訓練有助於 Claude 更好地適應您法律領域的特定需求，提升其依照您的標準摘要文件的能力。

4. **反覆改進：** 微調並非一次性的流程。隨著 Claude 持續產生摘要，您可以反覆加入其表現不佳的新範例，進一步精進其能力。隨著時間推移，這種持續的回饋循環將造就一個高度專精於您法律文件摘要任務的模型。

<Tip>
  微調目前僅透過 Amazon Bedrock 提供。更多細節請參閱 

  [AWS 發布部落格](https://aws.amazon.com/blogs/machine-learning/fine-tune-anthropics-claude-3-haiku-in-amazon-bedrock-to-boost-model-accuracy-and-quality/)

  。
</Tip>

<CardGroup cols={2}>
  <Card title="摘要 cookbook" icon="link" href="https://platform.claude.com/cookbook/capabilities-summarization-guide">
    查看如何使用 Claude 摘要合約的完整程式碼實作範例。
  </Card>

  <Card title="引用 cookbook" icon="link" href="https://platform.claude.com/cookbook/misc-using-citations">
    探索引用 cookbook 範例，了解如何確保資訊的準確性與可解釋性。
  </Card>
</CardGroup>
