0Pricing
AI Prompt Engineering · 课时

层次化摘要

渐进式压缩:章节 → 部分 → 文档摘要

层次化摘要 是 CoddyKit 上的免费 AI Prompt Engineering 课时。 这是第 3 节课,共 4 节。 你可以在下方免费阅读本课时的完整内容 — 然后在浏览器中使用内置代码编辑器和全天候 AI 导师进行实践。 这是 AI Prompt Engineering 学习路径的一部分,你的进度在网页和 CoddyKit 应用中同步。 AI Prompt Engineering 课程共包含 4 节课。

什么是层级式摘要?

层级式摘要反映文档本身的结构。它不会平等地处理所有文本块,而是逐层压缩内容:

  • 页面 → 章节摘要
  • 章节 → 小节摘要
  • 章节 → 文档摘要

每个层级都是其下一级内容的压缩表示。这正是人类总结书籍的方式——阅读章节,形成心中的摘要,然后进行整合。

何时使用层级式摘要

以下情况适合使用层级式摘要:

  • 书籍:超过 200 页且具有清晰的章节结构
  • 研究论文:摘要、引言、方法、结果、讨论
  • 法律合同:包含明确标题的章节(定义、义务、终止)
  • 技术报告:执行摘要 → 研究结果 → 附录

对于短文来说,这种方法没有必要。当文档具有自然的树状结构时,它最能发挥作用。

文档树结构

将文档建模为一棵树:

  • 根节点:最终摘要
  • 第 1 层节点:章节摘要
  • 第 2 层节点:小节摘要
  • 叶节点:原始页面或文本块内容

摘要过程自底向上进行:叶节点 → 第 2 层 → 第 1 层 → 根节点。每个节点的摘要仅根据其子节点的摘要生成。

from dataclasses import dataclass, field
from typing import List, Optional

@dataclass
class DocNode:
    title: str
    content: str = ''
    summary: str = ''
    children: List['DocNode'] = field(default_factory=list)

# Example: book with 3 chapters, each with 3 sections
book = DocNode(
    title='My Book',
    children=[
        DocNode('Chapter 1', children=[
            DocNode('Section 1.1', content='...raw text...'),
            DocNode('Section 1.2', content='...raw text...'),
        ]),
        DocNode('Chapter 2', children=[
            DocNode('Section 2.1', content='...raw text...'),
        ])
    ]
)

自底向上摘要

从底层向上遍历这棵树。叶节点根据其原始内容生成摘要,内部节点根据其子节点的摘要生成摘要。

import openai
client = openai.OpenAI(api_key='sk-...')

def summarize_text(text, role='section'):
    resp = client.chat.completions.create(
        model='gpt-4o',
        messages=[
            {'role': 'system',
             'content': f'Summarize this {role} in 3-5 sentences.'},
            {'role': 'user', 'content': text}
        ]
    )
    return resp.choices[0].message.content

def summarize_tree(node, depth=0):
    role = ['document', 'chapter', 'section', 'page'][min(depth, 3)]
    if not node.children:
        node.summary = summarize_text(node.content, role)
    else:
        for child in node.children:
            summarize_tree(child, depth + 1)
        combined = '\n\n'.join(
            f'{c.title}:\n{c.summary}' for c in node.children
        )
        node.summary = summarize_text(combined, role)
    return node.summary

渐进式压缩

渐进式压缩意味着每个层级都会降低信息密度。一个实用的经验规则是:

  • 页面(2000 个词元)→ 小节摘要(200 个词元)——压缩 10 倍
  • 小节摘要(200 个词元)→ 章节摘要(100 个词元)——压缩 2 倍
  • 章节摘要(5 × 100 个词元)→ 文档摘要(150 个词元)——压缩约 3 倍

总计:将一份 10,000 词元的文档压缩到约 150 个词元,同时保留主要论点。提示每个层级保持相应的压缩比。

PAGE_PROMPT = 'Summarize this page in 2-3 sentences (under 80 words).'
SECTION_PROMPT = 'Given these page summaries, write a section summary in 3-4 sentences (under 120 words).'
CHAPTER_PROMPT = 'Given these section summaries, write a chapter summary in 4-5 sentences (under 150 words).'
DOC_PROMPT = 'Given these chapter summaries, write an executive summary of the entire document (under 200 words).'

保持各层级之间的连贯性

层级式摘要存在一个风险:同一层级的摘要可能彼此矛盾或重复,而且这些错误会在向上汇总时不断累积。以下策略有助于保持连贯性:

  • 在提示词中包含父级章节标题,让模型了解上下文
  • 要求模型避免重复之前章节摘要中已经陈述的事实
  • 在最终归约步骤中,明确要求模型解决任何矛盾
def summarize_sections_for_chapter(chapter_title, section_summaries):
    content = '\n\n'.join(
        f'Section: {s["title"]}\n{s["summary"]}'
        for s in section_summaries
    )
    prompt = (
        f'Chapter: {chapter_title}\n\n'
        'Below are summaries of each section. '
        'Write a unified chapter summary without repeating '
        'the same facts from multiple sections.\n\n' + content
    )
    resp = client.chat.completions.create(
        model='gpt-4o',
        messages=[{'role': 'user', 'content': prompt}]
    )
    return resp.choices[0].message.content

研究论文的层级结构

研究论文具有自然的层级结构:摘要 → 引言 → 方法 → 结果 → 讨论 → 结论。每个章节的职责各不相同,因此应使用针对章节的提示词:

SECTION_PROMPTS = {
    'abstract': 'Summarize the paper abstract: what problem, method, and result?',
    'introduction': 'Summarize the introduction: what gap does the paper address?',
    'methods': 'Summarize the methods: what approach was used?',
    'results': 'Summarize the results: what were the key findings and metrics?',
    'discussion': 'Summarize the discussion: what do the results mean?',
    'conclusion': 'Summarize the conclusion and future work.'
}

def summarize_paper(sections_dict):
    section_summaries = {}
    for section, text in sections_dict.items():
        prompt = SECTION_PROMPTS.get(section, 'Summarize this section.')
        section_summaries[section] = call_llm(prompt, text)
    return section_summaries

法律合同的层级结构

法律合同遵循条款层级:定义 → 义务 → 救济措施 → 终止 → 适用法律。层级式摘要必须保留:

  • 精确数值(付款金额、截止日期)
  • 当事方名称(客户、供应商、许可方)
  • 条件性表述(除非、除非在……时、前提是)

提示模型标记正在摘要的任何包含数值金额或条件性表述的条款,避免其被意外遗漏。

LEGAL_PROMPT = '''Summarize this contract clause in plain English.
Preserve: all monetary amounts, dates, party names, and conditionals.
Flag any obligation with [OBLIGATION] and any amount with [AMOUNT].'''

def summarize_clause(clause_text):
    resp = client.chat.completions.create(
        model='gpt-4o',
        messages=[
            {'role': 'system', 'content': LEGAL_PROMPT},
            {'role': 'user', 'content': clause_text}
        ]
    )
    return resp.choices[0].message.content

存储层级式摘要

请存储完整的摘要树,而不仅仅是根节点摘要。这样可以实现:

  • 下钻查看——按需显示章节摘要,然后显示小节摘要
  • 检索——针对小节摘要而不是整个文档匹配用户查询
  • 更新——当某个小节发生变化时,只需重新生成该分支的摘要
import json

def tree_to_dict(node):
    return {
        'title': node.title,
        'summary': node.summary,
        'children': [tree_to_dict(c) for c in node.children]
    }

def save_tree(node, path):
    with open(path, 'w') as f:
        json.dump(tree_to_dict(node), f, indent=2)
    print(f'Saved summary tree to {path}')

增量更新

文档更新时,层级结构支持增量重新摘要。只需重新摘要被修改的节点及其祖先节点,所有兄弟分支仍然有效。

以一本共 10 章的书为例,如果第 3 章经过修订:重新摘要第 3 章的小节,然后重新摘要第 3 章,最后重新摘要整本书。这样只需重新计算 3 个节点,而不是所有节点。

def update_node(node, updated_child_title):
    # Re-summarize the changed child
    for child in node.children:
        if child.title == updated_child_title:
            summarize_tree(child)  # re-summarize from leaves
            break
    # Re-summarize current node from updated children
    combined = '\n\n'.join(
        f'{c.title}:\n{c.summary}' for c in node.children
    )
    node.summary = summarize_text(combined)
    return node.summary

扁平式与层级式的比较

扁平式映射-归约与层级式摘要的比较:

  • 扁平式:更简单,忽略文档结构,更适合结构均一的文档(新闻文章)
  • 层级式:遵循文档结构,支持下钻查看,对结构化文档的连贯性更好

在实际应用中,可以将两者结合起来:在每个章节内部使用扁平式映射-归约处理大量页面,然后跨章节使用层级式摘要。这是处理现实文档最稳健的方法。

知识检查

在层级式摘要中,摘要过程沿文档树的哪个方向进行?

回顾:层级式摘要

层级式摘要反映文档结构,可以获得更好的结果:

  • 将文档建模为一棵树:页面 → 小节 → 章节 → 文档
  • 自底向上进行摘要:先处理叶节点,最后处理根节点
  • 每个层级应用渐进式压缩以保持连贯性
  • 最适合具有清晰层级结构的书籍、研究论文和法律合同
  • 存储完整的树,以支持下钻检索和增量更新

下一课:通过重叠和滚动摘要保持跨文本块的上下文。

常见问题解答

「层次化摘要」课时是免费的吗?

是的 — 「层次化摘要」的完整文本可在网页上免费阅读。要进行交互式练习(内置代码编辑器和全天候 AI 导师)并解锁 AI Prompt Engineering 课程的其余内容,请升级到 CoddyKit PRO。 AI Prompt Engineering 课程共包含 4 节课。

「层次化摘要」这节课中我会学到什么?

渐进式压缩:章节 → 部分 → 文档摘要 你通过在浏览器中直接运行的动手代码来练习 AI Prompt Engineering,全天候 AI 导师会在你学习这节课的过程中回答你的问题。

学习 AI Prompt Engineering 需要有经验吗?

无需任何先前经验。CoddyKit 上的 AI Prompt Engineering 课程适合初学者到高级学习者,你可以从这里开始或从头开始,按照自己的节奏学习。 这是第 3 节课,共 4 节。

「层次化摘要」课时需要多长时间?

大多数 CoddyKit 课程大约需要 5–10 分钟。每节课都很精短且互动,所以你能稳步进步,并在网页和应用中从离开的地方继续。

我能在这节 AI Prompt Engineering 课中编写并运行代码吗?

能。每节 AI Prompt Engineering 课都包含内置代码编辑器,你可以在浏览器中直接编写并运行真实代码,并获得即时 AI 反馈 — 无需本地设置。

此课程中的所有课时

  1. 长文本分块策略
  2. Map-Reduce 摘要模式
  3. 层次化摘要
  4. 在文本块之间保持上下文
← 返回 AI Prompt Engineering