type
Post
status
Published
date
Sep 10, 2025
slug
summary
tags
prompt
人工智能
category
技术分享
icon
password
在
ChatPromptTemplate 中,MessagesPlaceholder 的作用可以概括为:为一组“不确定数量”的消息对象在 Prompt 中预留一个“动态占位符”。如果说
{question} 是为一个字符串(String)预留的座位,那么 MessagesPlaceholder 就是为一排消息对象列表(List of Messages)预留的一个“VIP 专区”。以下是它的核心作用拆解:
1. 处理“列表”而非“字符串”
普通的变量占位符(如
{question})通常只能接收一个简单的字符串。 如果你尝试把一段对话历史(包含多个 HumanMessage 和 AIMessage 的列表)塞进 {history} 字符串占位符,结果会变成一段很难看的 Python 代码文本:[HumanMessage(content='你好'), AIMessage(content='你好!')]
而
MessagesPlaceholder 会告诉 LangChain:“这里会进来一串完整的消息对象,请把它们原封不动地展开并插入到这个位置。”2. 保持消息的角色(Role)属性
使用
MessagesPlaceholder 后,历史记录中的每一条消息都能保留其原始身份:- 用户说的话依然是
HumanMessage。
- AI 说的话依然是
AIMessage。
这样发送给模型(如 DeepSeek 或 GPT)时,模型能清晰地识别出:“这是之前用户说的,那是之前我回答的”,从而大大提高上下文理解的准确度。
3. 实现“动态插入”
在你的代码结构中:
- System Message: 始终在最开头(定义角色)。
- MessagesPlaceholder (history): 动态地把过去 5 轮或 10 轮的对话塞在这里。
- Human Message (question): 始终在最后(当前用户的新问题)。
这种结构非常符合大模型的对话规范:[系统指令] -> [历史对话] -> [最新提问]。
形象的比喻
想象你在排队入场:
("system", "..."):是一个固定的领队。
("human", "{question}"):是一个固定的末尾观众。
MessagesPlaceholder(variable_name='history'):是中间的一块预留区域。
当程序运行起来后,Memory 组件会带着一队人(历史消息)走过来。
MessagesPlaceholder 就会退场,让这一队人原样站进这个预留位置。代码中的逻辑连接点
这个
variable_name='history' 必须与两处保持一致:- Memory 定义处:
ConversationBufferMemory(memory_key="history", return_messages=True)
- 数据注入处:
RunnablePassthrough.assign(history=...)
总结一句话: 没有它,你的对话历史只是一段死板的文字;有了它,你的对话历史才是活生生的、有角色区分的消息流。
- Author:guderain
- URL:https://wangguanxi.space/article/2e02b727-a3a3-807e-b4b9-c74425fe08d9
- Copyright:All articles in this blog, except for special statements, adopt BY-NC-SA agreement. Please indicate the source!
Relate Posts


.webp?table=collection&id=92be88af-5f71-4631-9d3e-ee3bd53dcced&t=92be88af-5f71-4631-9d3e-ee3bd53dcced&width=1080&cache=v2)