一聚教程网:一个值得你收藏的教程网站

最新下载

热门教程

理解 LangGraph 状态流转:State、Node 与 Reducer 如何协作

时间:2026-09-14 10:26:01 编辑:袖梨 来源:一聚教程网

在普通函数中,参数与返回值通常足以描述数据流;但进入多步骤的智能体工作流后,用户输入、工具结果和中间结论需要持续共享。LangGraph 用 State 保存上下文,由 Node 产生局部更新,再交给 Reducer 决定合并方式。理解这套运行模型,是正确组织复杂流程的基础。

这一篇只解决一个问题:

LangGraph 中的数据是如何在节点之间流转的?

不要先背 API,先理解它的运行模型。


1. 为什么 Agent 需要 State?

普通函数:

function add(a, b) {
  return a + b;
}

数据通过参数传递:

输入
 ↓
函数
 ↓
输出

但是 Agent 工作流:

用户输入

↓

分析任务

↓

调用工具

↓

获取结果

↓

总结回答

中间会产生大量数据:

例如:

{
  question:"查询订单",
  userId:"1001",
  orderInfo:{},
  toolResult:"",
  answer:""
}

这些数据需要在不同步骤之间共享。

所以 LangGraph 引入:

State(状态)


2. State 是什么?

State 可以理解为:

整个 Graph 执行过程中的共享数据对象。

例如:

{
  query:"",
  answer:""
}

流程开始:

State

{
 query:"1+2",
 answer:""
}

经过节点:

Node

↓

更新 State

↓

{
 query:"1+2",
 answer:"3"
}

3. 如何定义 State?

LangGraph 使用:

Annotation.Root()

定义状态结构。

例如:

const StateAnnotation = Annotation.Root({

  query: Annotation({
    reducer: (_prev,next)=>next,
    default:()=> ""
  }),

  answer: Annotation({
    reducer: (_prev,next)=>next,
    default:()=> ""
  })

});

表示:

我们的 State 有两个字段:

State

├── query
└── answer

4. Node 是什么?

Node 就是一个执行步骤。

本质:

(state)=>update

例如:

const answerNode = (state)=>{

  return {
    answer:`你的问题是:${state.query}`
  }

}

输入:

{
 query:"hello",
 answer:""
}

返回:

{
 answer:"你的问题是:hello"
}

注意:

Node 不直接修改 State。

错误:

state.answer="xxx"

LangGraph 推荐:

return {
 answer:"xxx"
}

为什么?

因为 LangGraph 会统一管理:

  • 状态更新
  • 状态合并
  • 历史保存

5. Node 返回的是完整 State 吗?

不是。

这是很多人的第一个疑惑。

比如:

当前 State:

{
 query:"hello",
 answer:""
}

Node:

return {
 answer:"你好"
}

不是变成:

{
 answer:"你好"
}

而是:

LangGraph 合并:

{
 query:"hello",
 answer:"你好"
}

所以:

Node 返回的是 State 的部分更新。


6. Reducer 是干什么的?

问题:

如果多个节点修改同一个字段怎么办?

例如:

两个节点:

Node1:

return {
 messages:["hello"]
}

Node2:

return {
 messages:["world"]
}

最终:

messages?

怎么办?

这就是 Reducer 的作用。


覆盖模式

默认:

(prev,next)=>next

表示:

新的覆盖旧的。

例如:

之前:

answer:"A"

节点返回:

answer:"B"

结果:

answer:"B"

累积模式

聊天记录:

messages: Annotation({

 reducer:(prev,next)=>[
   ...prev,
   ...next
 ]

})

第一次:

[ "你好"]

第二次:

[ "你好", "你好,请问..."]

7. 一个完整 Demo

状态:

const StateAnnotation = Annotation.Root({

 text:Annotation({
   reducer:(prev,next)=>next,
   default:()=> ""
 })

});

节点:

const step1=(state)=>({

 text:`${state.text}->step1`

});


const step2=(state)=>({

 text:`${state.text}->step2`

});

流程:

START

↓

step1

↓

step2

↓

END

输入:

{
 text:"hello"
}

执行:

第一次:

hello

↓

hello->step1

第二次:

hello->step1

↓

hello->step1->step2

最终:

{
 text:"hello->step1->step2"
}

8. 用一句话理解 State + Node

不要记 API。

记这个模型:

当前 State

    ↓

Node读取

    ↓

Node返回部分更新

    ↓

Reducer合并

    ↓

新的 State

    ↓

下一个 Node

总结

LangGraph 的状态模型:

概念作用
State保存整个工作流的数据
Node执行任务并返回状态更新
Reducer决定状态如何合并
Annotation定义 State 结构

一句话:

LangGraph 通过 State 在节点之间传递上下文,Node 负责产生状态更新,Reducer 负责控制更新方式,从而让整个 Agent 工作流能够持续演进。

热门栏目