RAG DEMO · 马自立的第二大脑

对我的笔记库提问

一个真实在用的个人知识库(Obsidian,记了四年的概念笔记、读书笔记、日记摘录和博客),公开部分放到线上。问一个问题,它先在 两万多 个笔记块里混合检索,再重排、带出处地回答;库里没有的,它会说没有。下面把每一步的分数都摊开了。

提问

检索过程

这一问在线上实际走过的每一步,上面的动画就是按这些数字放的。蓝底的行是最后放进提示词、给模型看的块。

这几列是什么

余弦:问题向量和块向量的相似度(bge-m3)。BM25:字面检索的分(中文两字切词)。混合分:两者各自换成 z 分(离平均值几个标准差)后按 1 : 0.15 相加,空壳块(不到 12 个字)减 3,过 1.5 才算候选。重排:bge-reranker-v2-m3 把问题和块成对打的相关度(0–1),候选按它重新排序。

怎么做的

检索的打分口径和我本地 Obsidian 插件「第二大脑」是同一套(同一份代码移植过来),本地那套先用评测集调过;线上版补上了重排、生成和生成评测。

01 · 离线
圈语料 + 切块
  • 只放知识类文件夹、博客、日记里的摘录块
  • 块级隐私过滤:私人关系、学生、钱、健康等规则
  • 日记一条一块,长块按子项再切,子块带上「页名 › 小标题 › 母块」
02 · 离线
算向量、打包
  • bge-m3,1024 维
  • 按内容哈希缓存,改了才重算
  • int8 量化,索引约 20 MB,随函数一起部署
03 · 在线
混合检索 → 重排
  • 先按问题里的时间 / 文件夹圈范围(「2023 年 3 月」「去年」「编程与技术里」)
  • 余弦 + BM25 的 z 分融合,取前 30
  • bge-reranker-v2-m3 精排
04 · 在线
拒答 or 生成
  • 两道门槛:前 10 最高余弦、重排最高分
  • 过线才把前 6 块交给 DeepSeek
  • 每句标出处 [n];片段答不了就说没写到

评测

在这份公开语料上单独建的评测集,召回和生成分开评。

边界和局限

  • 只放了公开的部分。日记的其余部分、人物、健康、资产等目录不进;进来的块还按规则逐块过滤(链到私密页面的、涉及身边人的、手机号 / 钱 / 就医等),过滤清单人工看过。
  • 笔记里很多是摘录。回答引用的可能是我摘的别人的话,不一定是我的观点,出处里能看到原文。
  • 评测规模小。一个人出题、一个人标注,数字只说明「在这份语料上」的表现。
  • 限流。每人每天 5 次(按北京时间零点清零),问过的问题当天直接回放,回放也算一次。