Chunk 学习笔记
Chunk 学习笔记
1. 什么是 Chunk
在 embedding、检索和 RAG 场景里,chunk 指的是把原始文档切成一段一段可独立编码、可独立检索的小文本单元。
对应的过程通常叫:
- chunking
- 文本切块
- 文档切分
可以先把 chunk 看成检索流程里的最小工作单元。它不是随便切一刀,而是既要保留语义完整性,也要方便后续编码和检索。
2. 为什么要做 Chunk
原始文档通常不适合整篇直接送去做 embedding 或检索,原因一般有三个:
- 太长,超过模型输入限制
- 粒度太粗,检索结果不精准
- 一篇文档往往包含多个主题,整篇编码会让语义混在一起
切块的目的,是让每一块:
- 尽量只表达一个相对完整的意思
- 长度不要太长,避免语义被稀释
- 长度也不要太短,避免上下文不足
3. Chunk 对检索效果为什么这么关键
检索效果不好时,很多人的第一反应是换 embedding 模型,但工程里更常见的问题其实出在 chunk 策略。
实际项目里,chunk 策略会直接影响:
- 向量质量
- 召回命中率
- rerank 效果
- 最终 LLM 回答质量
常见问题包括:
- chunk 太大,相关信息被埋在长文本里,召回不准
- chunk 太碎,单块语义不完整,召回上来后也不好用
- 切断了标题和正文的关系,导致上下文丢失
- overlap 设置不合理,重复太多或连续性不够
所以可以把它理解成:
embedding 决定“怎么表示”,chunking 决定“切得对不对”。
4. 一个好 Chunk 的目标
好的 chunk 通常要满足这几个条件:
- 语义尽量完整
- 长度尽量稳定
- 有明确边界
- 便于加标题、来源、页码等元数据
- 便于后续召回、去重、引用和展示
如果一个 chunk 满足下面任意一种情况,通常都说明切得不够好:
- 只有一句残缺的话
- 标题和正文被拆开
- 一个 chunk 同时塞了多个不相关主题
- 文本大部分是模板、导航、页脚、噪声内容
5. 常见的 Chunk 策略
5.1 固定长度切块
例如每 300 字、每 500 tokens 切一块。
优点:
- 简单
- 稳定
- 容易批量处理
缺点:
- 可能把完整段落或完整论点切断
适合:
- 初版 baseline
- 结构不稳定的原始文本
5.2 按段落切块
按照自然段来切。
优点:
- 语义边界自然
- 可读性通常更好
缺点:
- 长度不稳定
- 某些段落可能过长或过短
适合:
- 普通说明文档
- 笔记
- 博客文章
5.3 按标题和小节切块
按照文档层级来切,例如:
- 一级标题
- 二级标题
- 小节内容
优点:
- 结构清晰
- 更适合知识库和技术文档
缺点:
- 某些小节可能太长,还需要二次细分
适合:
- API 文档
- 产品文档
- 教程型内容
5.4 混合切块
先按标题或段落切,再对过长部分按固定长度继续细分。
这是实际项目里很常见的一种方案,因为它兼顾了:
- 语义完整性
- 长度可控
- 工程实现难度
6. 什么是 Overlap
overlap 是相邻 chunk 之间保留的一部分重复内容。
作用:
- 避免关键信息刚好被切断
- 提高上下文连续性
- 减少边界句子丢信息的问题
例如:
- chunk1: 第
1~300字 - chunk2: 第
260~560字
这里就有 40 字重叠。
但 overlap 也不是越大越好。
如果 overlap 太大,会带来:
- 存储冗余
- 检索结果重复
- top-k 被相似 chunk 挤占
因此,overlap 要处理的是下面这组平衡:
- 上下文连续性
- 检索去重成本
7. Chunk Size 怎么定
chunk 大小没有全场景通用的固定答案,应该结合下面几件事一起看:
- 文档类型
- 模型最大输入长度
- 用户 query 的粒度
- 是否有 rerank
- LLM 最终要吃多少上下文
7.1 中文场景一个常见起点
如果是中文知识库、普通笔记或教程类文本,可以先从下面这个 baseline 开始:
- 每块
300~500字 - overlap 取
10%~20% - 优先按标题和段落切,超长再二次切分
这不是固定标准,但很适合作为第一版默认策略。
7.2 用 token 还是字数
更严格的工程实现通常按 token 控制,因为模型真正受限的是 token 数。
但在中文笔记场景里:
- 用字数做初版规则更直观
- 用 token 做最终线上控制更稳妥
8. 不同文档类型怎么切
8.1 FAQ
优先按一问一答切。
原因:
- 每条 FAQ 本身就是天然语义单元
- 非常适合检索
8.2 API 文档
优先按接口、参数、返回值、错误码分块。
原因:
- 用户检索时往往是精确问题
- 结构化切分更利于命中
8.3 教程和博客
优先按标题和段落切,再对过长部分二次细分。
原因:
- 这类文档有明显章节结构
- 语义常围绕小节展开
8.4 法规、合同、制度文档
优先按条款、章节切,再保留章节编号。
原因:
- 编号本身很重要
- 后续引用和回溯都依赖这些元数据
9. Chunk 不只是文本,还要带元数据
实际工程里,向量库里存的往往不只是 chunk 文本本身,还包括一组元数据。
常见字段:
chunk_iddoc_idtitlesectionsourcepageurlcreate_time
这些元数据很重要,因为它们会影响:
- 过滤
- 去重
- 排序
- 页面展示
- 来源追踪
一句话说:
没有元数据的 chunk,很难在真实系统里长期维护。
10. Chunk 怎么评估好不好
chunk 没有一个单独的万能评分,通常要放到检索链路里一起评估。
最常见的评估方式有:
- 看 Recall@K 是否提升
- 看 badcase 是否减少
- 看召回结果是否更少重复
- 看 LLM 最终回答是否更稳定
排查时,通常先看这几个问题:
- 召回不到,是不是 chunk 太大
- 召回到了但答不好,是不是 chunk 太碎
- top-k 很重复,是不是 overlap 太大
- 标题命中了但正文没进来,是不是标题和内容被拆开了
11. 常见坑
11.1 只按固定长度切,不看语义边界
这样最容易把一句完整的话切断。
11.2 标题和正文分离
很多技术文档里,标题本身就是关键检索信号,和正文拆开后效果通常会明显变差。
11.3 chunk 太碎
如果一个 chunk 只剩一句短句,虽然向量容易算,但语义往往不完整。
11.4 chunk 太大
如果一块里塞进多个主题,检索时很容易语义发散。
11.5 overlap 太大
会导致召回结果里出现很多几乎一样的片段,影响 top-k 质量。
11.6 没做清洗就直接切
页眉、页脚、导航栏、版权信息、空白符噪声,都会污染 chunk 质量。
12. 一个实用的默认方案
如果你是第一次给中文知识库做 chunk,可以先这样做:
- 先清洗无关噪声
- 按标题和段落切
- 过长段落按
300~500字继续切 - overlap 先取
10%~15% - 保留
doc_id、title、section、source - 离线抽样检查 top-k 检索效果
- 根据 badcase 再回调 chunk size 和 overlap
这套方案不是最优,但通常足够当第一版生产 baseline。
13. Chunk、Embedding、RAG 的关系
可以把三者简单理解成:
- chunking 决定“怎么切”
- embedding 决定“怎么表示”
- retrieval / rerank 决定“怎么找”
- LLM 决定“怎么答”
如果 chunk 切得不对,后面的 embedding、rerank、LLM 往往都只能被动补救。
14. 一句话总结
Chunk 的核心不是“把文档切小”,而是:
把文档切成既适合向量表示、又适合检索召回、还能支撑最终回答的语义单元。