我的毕设是关于 AI 桌宠的长期陪伴,主要工作是桌宠系统的设计,但为了在长上下文以及跨对话保持记忆以及抑制人设偏移,我也缝了一个长期记忆模块。
这块会有点小硬核,原本是分几篇结合论文进行剖析的,但遗失了,我只是简单概括主线。
为什么需要外置记忆?
首先是为啥需要外置的长期记忆系统,因为目前所使用的 GPT、Claude、DeepSeek 模型本质都是无状态推理(LLM 把每次输入的所有上下文作为一次输入,然后给出一次输出)。而不同 LLM 的上下文窗口上限不同,通常在 200K 到 1M tokens 之间。而且这个上下文窗口并不等效于有效上下文,即还未达到标定的窗口前,就已经出现了性能下降、幻觉,或者如 Attention is Limited - Lost in the Middle 里提到的 U 形曲线,大模型会”遗忘中间”。
所以不管是为了新开上下文后能够记得以前的东西,或者减缓性能下降,记忆系统都是有必要的。至于为什么是外置的,是为了避免占用上下文,只在需要的时候插入和引导。
因为之前的架构剖析因为 云服务商跑路后:再次审视个人博客的形态与值得被记录的东西 的缘故丢了。所以这里简单再聊一下当下 LLM 的长期记忆方案主要分为几种。
三种记忆方案
方案一:基于 Markdown 由 LLM 自己管理读取和写入(OpenClaw)
项目代表比如 MemSearch,它被 OpenClaw 使用或者说原理一致。
它根据 Agent.md、Memory.md、Identity.md、User.md 等文件来管理 Agent 的行为、记忆节点、自我认知、用户偏好等主要信息。所有文件以 Markdown 形式写入和读取。
NOTE
- 源文件人类直接可读、可维护
- 不需要额外 embedding 或数据库的开销和复杂度
- 用来控制偏好或语言风格的效果显著
WARNING
- 一般只在启动时完整注入,长上下文下人设会逐渐偏移重置为 LLM 默认风格
- 写入和读取的时机(触发条件)不可控,触发率很低,非常依赖 LLM 自身智商。Claude 表现较佳
- 不适合做长时间线的事实记录,记录越多就越容易稀释提示词中原本的重点
方案二:基于 RAG 的向量化与相似度匹配(Mem0)
它会实时地捕获用户和 LLM 产生的对话数据,用 LLM 提取有效信息,比如:
用户:我最近那个桌宠毕设项目里的长期记忆系统真难做。LLM: XXXXXX可能会提取出来两条记忆:“用户的毕设是包含长期记忆系统的”、“用户觉得毕设很难做”。
这个提取的格式或者内容可以通过提示词来自己定。
然后这两条记忆会被向量化存入数据库,最后每次用户有新提问的时候都会做比对用户提问向量和数据库内向量的相似度,选取 top-n 作为依据插入辅助 LLM 回复。
提问时写入,提问时注入。 记忆像滚雪球一样滚起来。
当然还有遗忘、重排那些东西但那些没在讨论范围内。
NOTE
- 外置且时序不敏感,非常适合长期记录事实性记忆
WARNING
- 依赖 embedding 这一额外步骤,需要额外的模型
- 写入的向量人类不可读,方向不可控,不能直接修正
- 写入条件很低,人为通常也需要反复清洗来保证质量
- 只是记得事实,而不是真的有灵魂(很难影响人设)
方案三:基于 Markdown 由多 Agent 不断整理归并(MemU)
这个我并没有实际地使用过,但了解过。
简单来说它用 LLM 自身的理解力替代了 embedding 模型的语义匹配。
对话 Agent 负责对话,另外有一组记忆 Agent,负责提取记忆、结构化元数据、形成关联图谱。而且记忆 Agent 不止在对话时工作,它的亮点在于即使没有对话正在发生,它也会像梦游一样不断地遍历、检索、遗忘、优化已有的记忆结构。就像人类通过睡觉来巩固记忆。
它最后输出的包含人类可读的 Markdown 作为源文件,也有关联图谱,也有 metadata 等等。
它在多项公开测试中都领先 Mem0,但我最后没选择它。

NOTE
- 记忆可读,结构比 MemSearch 那种单层结构优雅得多
- 无需 embedding 这层黑盒子中间层
WARNING
- 检索过程不会太快,记忆越多越快不起来,无法并行,受限于检索 LLM 本身的阅读总结速度
- Token 消耗量很高,Memory Agent 很挑模型,要权衡速度、理解能力、上下文长度、价格。Claude Haiku 和 DeepSeek-V4-Flash 是不错的选择
- 记忆数据超过 LLM 上下文窗口越多,性能越差
RAG 是否适合个人博客系统?
之所以产生这个疑问是先前我博客内容杂乱,而且通过简单的分类、标签很难概括和分清它们。最主要的是,很难体现出来博客之间的联系。
当时初学 RAG 时就想,能不能用 RAG 来发掘这种联系?
这个项目正是这么做的,它的作者是 时歌,他也围绕项目讨论过许多。
但是从出发点来看,它能否胜任博客系统内部展示?
向量相似度的局限
根据前面了解到的相关知识,可以知道 RAG 本身建立联系依赖于检索相似度(无论是向量语义匹配、关键词匹配还是混合检索)。抛开计算量、额外模型等复杂度不谈——它最终计算出来返回的是一篇文章中某一个文本块到另外一个文本块的连接。这个连接没有标明是什么联系,只是在数学上,这两个文本块的相关度高于设定的阈值。
和前面提到对话中提取有效记忆再转换向量不同,博客需要经过的处理是文本分块:把每篇博客按照一定长短分块,然后转换成向量。
所以得到了:一篇文章和另一篇文章之间的某个具体文本块之间存在着不知道、也许作者本身也讲不清楚的联系。重点在于,关系依然说不清道不明。
这意味着我烦恼的主要点依然没有得到解决:我无法同时清晰地完成对博客的分类,以及对不同博客之间联系的管理与展示。别人会觉得我的博客内容组织管理一团糟。
RAG 给不同博客带来了非常多、非常杂乱的关系连接,但是无法解释这种关系。
文本分块的短视性
同时这层关系连接本身就带有一种短视性。为什么说短视?问题就发生在文本分块。文本分块让这种关系分析本身就局限于一个小段落,甚至仅仅因为其中一句话。而通常作者希望这种联系是像主题阅读那种全局观,甚至完全只是一种 feeling。这种 feeling 或者全局观,是 RAG 所无法体现的。或者即使体现了,也淹没在了它所计算出来的大量低级联系当中。
到目前为止来看,RAG 本身是不适合直接作为个人博客内容的关系图谱展示的。
替代方案:引用图谱
如果想要展示博客之间的关联性,可以用引用图谱。
即文章 A 中引用了文章 B 或者相反,那么 A 和 B 之间就连接在一起。
这样的图谱虽然不够深层,但是可以反映出来直接联系。而且这层直接联系是由作者本身提供的,具有说服力。这样的图谱生成出来很简单,不至于连 node 之间的 edge 上都要有大量的注释。
而且在文末放置那篇文章所引用的完整链条也可以反馈出来一定的信息,引导用户阅读。
RAG 应该被用在哪里?
它不适合作为博客系统的展示,但是它适合作为个人知识库构建的一种伴生物,正如 YOLO 那样。
博客系统里面只要展示作者想给读者看到的就行(分类、标签、系列、书架、关联引用图谱)。
而 RAG,则是负责给作者本身发掘:你的文章里面可能还存在着某些这样子的联系。这样的联系也许是作者本身也很难解释说清的。而逐渐让这些联系成为一个可以被解释的、说清的主题,则是作者要做的事情。
所以说,博客系统是作者给读者准备的,而 RAG 是给作者自身准备的,它也许可以指引作者之后写什么。
同时,还一直忽略了一点:RAG 本身对数据量有需求。如果本身只有几十篇博客,那么 RAG 的收益是很低的;当博客来到数百篇乃至数千篇,那么 RAG 的收益会显著提升。因为这些隐晦的联系会清晰起来、收束起来,而不是都是单独的。
所以简单来说,RAG 是给那些有洞见的、且产量大的博主用的,而不是我这种三天打鱼两天晒网还很懒的鸽子。