返回博客
·AI技术

RAG 落地踩过的坑,比你想象的深

从 chunk 策略到向量检索,生产环境 RAG 系统踩坑实录,附解决方案。

#RAG#LLM#向量数据库

# RAG 落地踩过的坑,比你想象的深

背景

我们公司的产品有个"智能问答"功能,本质就是个 RAG 系统:用户提问 → 检索相关文档 → 喂给 LLM 生成回答。

看起来很简单对吧?三个步骤,每个都有现成方案。我们花了三个月才把准确率从 35% 提到 72%。以下是踩过的坑,按严重程度排序。

坑一:Chunk 策略选错了

最初我们用的策略是"按段落切分,每段 500 字"。这在技术博客场景下还行,但我们的产品文档有大量表格、代码块、层级标题。按段落切分后,一个完整的"配置说明"可能被切成三段,语义断裂。

换了策略:先按 Markdown 标题分层,每层内再按语义完整性切分,确保每个 chunk 包含一个完整的信息单元。chunk 大小控制在 300-600 tokens,用 overlap=50 防止边界信息丢失。

效果:检索准确率从 41% 提到 58%。

坑二:向量检索不够用

纯向量检索有个问题:它对关键词匹配不敏感。用户搜"如何重置密码",但文档里写的是"忘记密码后的恢复流程",语义相近但关键词不重叠,向量相似度可能很低。

解决方案:混合检索。向量检索 + BM25 关键词检索,然后用 Reciprocal Rank Fusion 合并排序。

// 简化的 RRF 合并逻辑

function rrfRank(vectorResults, keywordResults, k = 60) {

const scores = {};

vectorResults.forEach((doc, i) => {

scores[doc.id] = (scores[doc.id] || 0) + 1 / (k + i + 1);

});

keywordResults.forEach((doc, i) => {

scores[doc.id] = (scores[doc.id] || 0) + 1 / (k + i + 1);

});

return Object.entries(scores)

.sort((a, b) => b[1] - a[1])

.map(([id]) => id);

}

效果:关键词敏感查询的准确率从 33% 提到 61%。

坑三:没做检索后的重排序

向量检索返回的前 K 个结果,顺序不一定最优。我们加了个 cross-encoder 重排序模型(bge-reranker-large),把 top-20 的候选 re-rank 到 top-5。

这个步骤增加了约 200ms 延迟,但回答质量明显提升——LLM 看到的上下文更精准,生成的回答相关性和幻觉率都改善了。

坑四:Prompt 里没给检索来源的元数据

最初我们直接把检索到的文本塞进 prompt:

基于以下文档内容回答问题:{retrieved_text}

问题:{user_question}

问题是,LLM 不知道这些文本的标题、作者、更新时间。用户问"最新的 API 版本是什么",检索结果里可能混入了旧版文档,LLM 无法判断哪个是最新的。

改后的 prompt 加入了元数据:

以下是从文档库中检索到的相关内容(按相关性排序):

  • [标题] {title} | [更新时间] {updated_at} | [作者] {author}
  • {content}

    请基于以上内容回答问题,优先引用更新、更权威来源的信息。

    问题:{user_question}

    效果:时效性相关问题的准确率提升明显。

    坑五:没处理"我不知道"的情况

    最严重的一个 bug:当检索结果完全不相关时,LLM 仍然会"自信地"编造答案。这是 RAG 系统最典型的问题——hallucination。

    解决方案:加一个相关性阈值判断。如果最佳匹配的向量相似度低于 0.7(我们调过的值),直接返回"未在文档中找到相关内容",而不是让 LLM 瞎编。

    const SIMILARITY_THRESHOLD = 0.7;

    if (topResult.score < SIMILARITY_THRESHOLD) {

    return '抱歉,在现有文档中未找到相关说明。';

    }

    效果:幻觉回答率从约 40% 降到 8%。

    踩坑总结

    | 问题 | 解决方案 | 效果提升 |

    |------|----------|----------|

    | Chunk 策略不当 | 按语义单元切分 + overlap | +17% |

    | 纯向量检索 | 混合检索 + RRF | +28% |

    | 排序不精确 | Cross-encoder 重排序 | +11% |

    | 缺少元数据 | Prompt 加入来源信息 | +6% |

    | 幻觉问题 | 相似度阈值兜底 | 幻觉率 -32% |

    三个月,五个坑,每个都不大但叠加起来杀伤力惊人。RAG 看起来是"套娃",实际上调参的空间比想象中大多了。