跳到正文

RAG 文档 Chunk 划分策略怎么选?

固定长度、语义边界、滑动窗口等方法的优缺点与适用场景

原题:在检索增强生成(RAG)系统中,文档的chunk划分策略有哪些常见方法?不同策略(如固定长度、语义边界分割、滑动窗口等)各自的优缺点及适用场景是什么?

文档处理 · 腾讯真题

回答与解析

常见分块策略对比

1. 固定长度分块

  • 实现:按token数或字符数硬切分(如512 tokens)
  • 优点:实现简单、Embedding批次处理高效、便于控制上下文长度
  • 缺点:边界可能切断语义(如"深度学习...的优化方法"被拆开),导致检索片段不完整
  • 适用:通用场景、对延迟敏感、文档结构松散时

2. 语义边界分割

  • 实现:按句子(NLTK/spaCy)、段落(\n\n)、或主题模型(如BERTopic)切分
  • 优点:保留语义完整性,检索结果可读性强
  • 缺点:块大小不均,可能过长(超出模型窗口)或过短(信息密度低);主题分割计算开销大
  • 适用:法律合同、学术论文等结构清晰的文档

3. 滑动窗口/重叠分块

  • 实现:设定块大小与滑动步长,相邻块重叠;两者都作为待测变量,由同一评测集决定
  • 优点:避免边界信息丢失,保证上下文连贯性
  • 缺点:存储冗余增加(~2倍),检索可能返回重复内容需去重
  • 适用:对话历史、代码等强上下文依赖场景

4. 智能分块(进阶)

  • Agentic分块:用LLM判断断点(如"此处是否完成一个完整论点")
  • 结构化分块:针对Markdown、JSON、代码按语法树切分

选型建议

场景 推荐策略
快糙猛上线 固定长度 + 重叠
高精度问答 语义边界 + 滑动窗口
代码/表格 结构化分块 + 元数据标注

实际中常组合使用:先用语义边界粗分,再对过长块用滑动窗口细分。

学习建议

掌握常见chunk策略的原理与适用场景,结合实际RAG案例理解其对检索精度和生成效果的影响。

口语版讲法(约4分钟)

  • 一句话定位:chunk 本质是检索精度与上下文完整性的取舍
  • 固定长度 vs 语义边界:各适用什么场景,边界在哪
  • 滑动窗口解决边界问题,但冗余是代价,组合策略才是常态
  • 业务案例:企业 SOP 检索,语义分块 + 滑动窗口组合
  • 落地风险:块大小、去重、元数据,以及一个延伸可延伸点

好,这道题问的是 Chunk 划分策略,我觉得它本质上是在考一个取舍:你如何在检索精度和上下文完整性之间做平衡。因为 RAG 的召回质量,很大程度上取决于你切出来的块是不是既独立又完整。

先说最直接的固定长度分块,按多少 token 或者字符数硬切。这个方案好处是简单、快,Embedding 批量处理效率高,而且能精确控制上下文长度。但它有个硬伤,就是边界可能把一句话或者一个逻辑单元从中间切断。举个例子,如果一篇文档在讲「深度学习的优化方法」,其中一句刚好被拦腰截断,那检索时返回的片段可能就变成了「深度学习的优化」,意思就偏了。所以它只适合文档结构松散、对语义完整性要求不高的通用场景,比如新闻聚合或者日志检索。如果你要快速上线一个 MVP,用这个没问题,但追求高精度问答就不行。

再一个就是语义边界分割,按句子、段落或者主题来切。这个能最大程度保留语义完整,检索回来的片段读起来通顺、可理解。但代价是块大小不均匀,有的块可能特别长,超出模型窗口;有的又特别短,信息密度低。而且像按主题切分,用 BERTopic 之类的模型,计算开销不小。它适合法律合同、学术论文这种结构清晰的文档,因为这些文档天然有段落和章节,切出来不会太离谱。

还有个常见的策略是滑动窗口,也叫重叠分块。它通过设定块大小和滑动步长,让相邻块有重叠。这么做的好处是彻底避免了边界信息丢失,比如一个关键概念跨了两块,重叠能保证至少有一块完整包含它。但代价也很明显,存储冗余,数据量可能翻倍,而且检索时可能返回多个高度相似的结果,需要额外去重。所以它适合对话历史、代码这类强上下文依赖的场景,比如你查一段代码,如果切断了函数定义和调用,那检索回来的就没法用。

真正落地的时候,我基本不会只用一种策略。通常是组合使用:先用语义边界粗分,保证核心块完整,然后对长度超过窗口的块,再用滑动窗口细分。举个例子,在企业 SOP 和合规文档检索里,文档结构很清晰,按章节切分后,有的章节特别长,比如「退款流程」可能包含好几页,这时候我就用滑动窗口把这一章切成几个 512 token 的块,步长设 256,这样既保证了语义边界,又控制了块大小。

这里有个坑一定要提:滑动窗口的冗余不是随便设的。步长太短,冗余太多,检索结果里全是重复信息;步长太长,重叠不够,又回到边界问题。我一般会先根据文档的平均句子长度来调,上线后监控 RAGAS 指标里的上下文精度,如果重复率太高就加大步长。另外,块大小不能超过 LLM 的上下文窗口,但也不能太小,否则信息密度低,Rerank 也救不回来。

还有一个方向我最近在关注,就是智能分块,比如用 LLM 自己判断断点,或者对 Markdown、JSON 按语法树切分。这个在代码或表格场景里效果很好,但代价是延迟和成本。如果面试官感兴趣,我可以展开讲讲结构化分块怎么跟元数据标注结合,来提升检索精度。

所以总结一下,我不会把 chunk 策略看成孤立的选择,我更倾向把它当成一个系统工程,结合文档结构、业务场景和上线指标来动态调整。没有银弹,关键是理解每种策略的代价,然后做取舍。

关键一句:智能分块(如 LLM 判断断点或语法树切分)在代码和表格场景中效果好,但延迟和成本是代价,可结合元数据标注优化。

面试官还可能这样问

  1. 问法 1 · 场景切入

    我看你做过电商知识库问答。假设用户问'怎么申请退款',系统检索到一段文档,但那一段刚好在'退款政策'和'退货流程'之间被切断了,回答就少了一半。你觉得这种情况怎么避免?你一般怎么切文档?

  2. 问法 2 · 层层追问

    RAG系统里文档怎么切块这个问题,你了解过哪些方法?……比如固定长度切块有什么坑?……那如果我想保证每个块语义完整,有什么更好的办法?……滑动窗口呢,什么场景下用?

  3. 问法 3 · 直球架构

    讲一下RAG里文档分块策略的常见方法,固定长度、语义边界、滑动窗口这些,各自优缺点和适用场景。你实际项目中怎么选型?

同模块相关题目