让AI记住我们聊过什么——对话记忆

上回学会了提示词模板、输出解析器、链式调用和流式输出。

现在AI已经能听懂人话、按格式输出了。

但还有一个问题:每次问AI,它都像第一次见你一样,完全不记得之前聊过什么。

你说“我叫小明”,它记住了。你再问“我叫什么”,它说“你没有告诉我”。

这就很尴尬了。

能不能让AI拥有“记忆”,记住上下文呢?

对话记忆(Memory),就是干这个的。

一、什么是对话记忆?

LangChain的Memory模块,用于在多次对话之间存储和传递历史信息,让模型具备“记住之前聊过什么”的能力。

作用:在对话中保留上下文,让AI的回答更连贯、更自然、更符合对话场景。

简单说就是:让AI从一个“健忘的路人”,变成一个“有记忆的朋友”。

比如你连续问AI三个问题:

你:“我叫小明。”
AI:“好的,小明。”

你:“我家养了一只猫叫汤姆。”
AI:“汤姆,记住了。”

你:“我叫什么?”
AI:“你没有告诉过我你的名字。”

最后那句就很出戏。前面明明说了名字,但AI转头就忘了。

Memory就是为了解决这个问题:

你:“我叫小明。”
AI:“好的,小明。”

你:“我家养了一只猫叫汤姆。”
AI:“汤姆,记住了。”

你:“我叫什么?”
AI:“你之前说你叫小明。”

虽然目前看到许多聊天机器人都是有记忆的,其实是借助了代码的帮助,提供了历史信息作为和LLM对话的上下文。

二、Memory的类型

LangChain提供了多种Memory类型,不同场景用不同的:

Memory类型 作用 适用场景
ConversationBufferMemory 把全部对话历史存下来 短对话、简单问答
ConversationBufferWindowMemory 只记住最近K轮对话 长对话、控制上下文长度
ConversationSummaryMemory 把对话内容压缩成摘要再存 超长对话,节省token
ConversationSummaryBufferMemory 摘要+最近几轮混合 折中方案
VectorStoreRetrieverMemory 用向量数据库存储,按相关性检索 海量对话、智能客服

新手入门,先用前两个就够了。

三、代码实战:ConversationBufferMemory

这是最简单的记忆方式——把所有的对话历史都存下来。完整存储所有对话历史,不做任何压缩或筛选。

  • 优点:保留全部细节,适合需要完整上下文的场景。
  • 缺点:Token消耗随对话线性增长,易超出模型上下文窗口限制。

代码如下:
from langchain.memory import ConversationBufferMemory
from langchain import ConversationChain
from langchain_community.llms import tongyi

# ==================== 配置 ====================
key = "your key"#替换为个人申请的api_key
llm = tongyi.Tongyi(api_key=key)

#创建一个记忆系统
memory = ConversationBufferMemory()
#创建会话链
conversation = ConversationChain(llm=llm,memory=memory,verbose=False)

print(conversation.predict(input="你好,我是一名程序员。"))
print(conversation.predict(input="你叫什么名字?"))
print(conversation.predict(input="我的职业是什么?"))

输出大概是这样:

第一轮:“你好!你平时都用什么软件写代码呢?”

第二轮:“我是通义模型。”

第三轮:“你是一名程序员。”

看到了吗?AI记住了三件事,而且后面两轮的回答都基于第一轮的信息。

四、代码实战:ConversationBufferWindowMemory

ConversationBufferWindowMemory是LangChain提供的一种记忆机制,只存储最近的K条对话记录(包括用户输入和模型输出),K是用户指定的窗口大小,表示保留多少轮对话(每轮对话包括一条用户消息和一条模型响应)。

当新的对话发生,最旧的对话会被移出窗口,确保内存和Token使用量保持在可控范围内。

特点

  • 滑动窗口机制:只保存最近K轮对话,新的对话会覆盖最早的对话记录。
  • 固定内存占用:无论对话进行多久,内存中只存储固定数量的对话记录,Token消耗不会随时间线性增长。
  • 可配置性:用户可以设置K参数,控制窗口大小,调整上下文的深度。

缺点

  • 丢失早期上下文:只保留最近的K条记录,早起的信息会被遗忘,影响对话的连贯性。
  • 不适合复杂场景:需要完整对话历史或长期依赖的场景(如法律咨询、长篇故事生成等),效果不如ConversationBufferMemory。
  • 窗口大小选择困难:设置合适的K需要权衡上下文完整性和资源消耗,过小可能导致信息不足,过大失去效率优势。

代码如下:
from langchain.memory import ConversationBufferWindowMemory
from langchain_community.llms import tongyi
from langchain.chains import ConversationChain

# ==================== 配置 ====================
key = "your key"#替换为个人申请的api_key
llm = tongyi.Tongyi(api_key=key)

#创建一个记忆系统
memory = ConversationBufferWindowMemory(k=1)
#创建会话链
conversation = ConversationChain(llm=llm,memory=memory)

conversation.predict(input="你好,我是一名程序员。")
conversation.predict(input="你叫什么名字?")
conversation.predict(input="我的职业是什么?")
#提取记忆
print(memory.buffer)

因为k=1只记住最近1轮,而“我是一名程序员”是第1轮说的,早就被挤出去了,所以AI的回答是:

“你没有告诉过我你的职业。”

这就是窗口记忆的特点:只记最近的,超过K轮的自动遗忘。

五、两种Memory对比

对比维度 BufferMemory(全量记忆) BufferWindowMemory(窗口记忆)
存什么 所有对话历史 只存最近K轮
优点 信息完整,不会丢 节省token,不会超限
缺点 对话越长越费钱 早期信息会丢失
适用场景 短对话(5轮以内) 长对话(10轮以上)

💡 建议: 刚开始用 k=3 或 k=5,看效果再调整。k太小容易“失忆”,k太大又费钱

有了记忆,AI就不再是“每次见面都像陌生人”了。

它开始像一个真正的对话伙伴——虽然不一定聪明,但至少不健忘。

posted @ 2026-06-24 11:44  测试木可  阅读(7)  评论(0)    收藏  举报