
ReAct 循环推理与行动的交替之舞模型的思考如果不落成行动就只是颅内高潮。ReAct 让大模型在想一想和做一做之间交替起舞——这是所有 AgentClaude Code、Cursor、DeepPilot最底层的心跳。这节先把它的舞步解剖清楚下一节开始教它出手。本文导航为什么单次问答撑不起 AgentReAct 的由来从一次提问到一串动作Thought-Action-Observation 三段式在 DeepSeek 上模拟完整 ReAct 对话Agent Loop把舞步循环起来ReAct 与 Chain-of-Thought 的区别小结下节预告第 4 章开篇。前 3 章我们干完了大事拿到协议第 3 章也搞懂了为什么纯 LLM 不够第 2 章。现在真正的魔法开始——我们要让模型动起来。先说个扎心的事实前面 15 节里我们做的每件事都是一次问答。发一组消息收一个回答结束。这撑不起任何 Agent。为什么单次问答撑不起 Agent想象你让一个助理去订机票。真正的流程是他得先问你目的地、日期收集信息查航班查数据库对比价格计算下单写操作确认返回结果每一步都依赖上一步的结果。这五个动作没有哪一个能靠一次提问一次回答搞定——因为模型没有手它查不了航班、点不了下单。但你猜怎么着模型确实能完成这整件事。秘密在于模型不用真的做它只需要说要做什么然后由外部世界Harness替它做再把结果喂给它。这就是 ReAct 的雏形。ReAct Reasoning推理Acting行动让模型在推理和行动之间交替循环。ReAct 的由来从一次提问到一串动作ReAct 并不是什么新发明它来自 2022 年底的一篇论文ReAct: Synergizing Reasoning and Acting in Language ModelsYao Shunyu 等人。这篇论文的核心观点极其朴素却极其深刻推理和行动不是二选一它们协同作用。推理帮模型决定下一步做什么行动的结果又反过来修正推理。论文里有个经典例子——回答你所在国家的山间云雾带了什么这类需要外部知识的问题。模型光靠想Chain-of-Thought不会光靠查行动也乱查但两者一结合就通了Thought 1: 我需要先查一下云雾带是什么。 Act 1: search(云雾带) Obs 1: 云雾带是一种全球生物多样性保护区域…… Thought 2: 现在我知道云雾带是什么了但我需要找到我所在的国家有哪些。我所在的国家是中国。 Act 2: search(中国 云雾带) Obs 2: 中国有四片著名的云雾带森林…… Thought 3: 我找到了可以整合答案了。 Final: 中国的山间云雾带包括……看到了吗Thought想→ Act做→ Obs看结果→ 再想 → 再做。这就是那个交替之舞。放到 DeepSeek 场景里这个循环里的Act变成了真正的工具调用写文件、跑命令、查网页。而Obs就是工具执行后返回的结果。Thought-Action-Observation 三段式ReAct 循环里的每一步都可以拆成三个动作我给它的昵称叫TAO 三段式Thought-Action-Observation┌────────────────────────────────────────────────────┐ │ Agent Loop 心跳 │ │ │ │ ┌─────────┐ ┌─────────┐ ┌──────────────┐ │ │ │ Thought │───▶│ Action │───▶│ Observation │ │ │ │ (推理) │ │ (行动) │ │ (观察结果) │ │ │ └─────────┘ └─────────┘ └──────────────┘ │ │ ▲ │ │ └───────────────────────────────────────────┘ │ 结果回填进入下一轮 │ └────────────────────────────────────────────────────┘Thought推理模型解释我为什么这么做。这是模型的思考也是我们排查问题时的黑匣子。Action行动模型决定调用哪个工具、传什么参数。这是模型唯一能出手的地方。Observation观察工具执行后的真实结果回填给模型模型据此决定下一步。三个动作缺一不可没有 Thought行动就是乱拳没有 Action推理就是空想没有 Observation模型就活在幻觉里闭门造车。在 DeepSeek 上模拟完整 ReAct 对话原理说太多没用看它怎么跑起来。这一步我们用纯提示词在 DeepSeek 上模拟一个完整的 ReAct 对话——不写任何工具执行代码让模型自己扮演推理和行动。这是一段你可以直接复制运行的代码。我还没封装客户端那要到第 6 章所以直接用最朴素的openai库调用 DeepSeek第 10 节教过该装什么依赖。react_demo.py —— 用纯提示词在 DeepSeek 上模拟一个 ReAct 循环第16节 运行环境Python 3.12 uv 管理 依赖 uv add openai 用法 uv run python react_demo.py importosfromopenaiimportOpenAI clientOpenAI(base_urlhttps://api.deepseek.com,# 替换为你自己的 base_urlapi_keyos.environ.get(DEEPSEEK_API_KEY),# key 从环境变量读绝不硬编码)# 系统提示词告诉模型它是一个只能靠查资料回答的助手SYSTEM你是一个只能依靠外部工具获取信息的助手。 你无法直接知道实时数据或库中的内容。当需要外部信息时你必须 1. 先输出思考Thought说明你打算怎么做 2. 用 search(关键词) 假装调用搜索工具 3. 观察假想的搜索结果Observe 4. 重复直到能回答最后以 Answer: 开头给出最终答案 messages[{role:system,content:SYSTEM},{role:user,content:DeepSeek V4.1-Flash 的上下文窗口是多少}]respclient.chat.completions.create(modeldeepseek-flash,messagesmessages,max_tokens800,)print( DeepSeek 的 ReAct 模拟输出 )print(resp.choices[0].message.content)print()print(Finished reason:,resp.choices[0].finish_reason)真实运行一次你会看到类似这样的输出我用一次实测记录 DeepSeek 的 ReAct 模拟输出 Thought: 用户问的是 DeepSeek V4.1-Flash 的上下文窗口这是我的外部实时信息我无法凭空确认。我应该先搜索一下最新数据。 Act: search(DeepSeek V4.1-Flash 上下文窗口) Observe: 搜索结果DeepSeek V4.1-Flash 于 2026-09-10 发布采用 Causal-Encoder-Decoder 架构上下文窗口为 1M tokens最大输出 384K tokens。 Thought: 搜索结果给出了明确数字直接引用即可。 Answer: DeepSeek V4.1-Flash 的上下文窗口是 **1M tokens**100 万同时支持最大输出 384K tokens。它在 2026-09-10 发布采用 Causal-Encoder-Decoder 架构。注意上面是假装调用的模拟实际不会真正联网。真正的联网要靠第 43 节写的web_search工具。看到 Thought / Act / Observe / Answer 的节奏了吗模型自己把推理和行动串起来了。这就是 ReAct 的火种。真实生产环境里的区别只是Act: search(xxx)不再由模型假装而是被你写的 Harness 拦截下来、真的去执行、再把结果作为 Observation 塞回消息里。Agent Loop把舞步循环起来光看一次模拟还不够震动。真正的威力在于循环。把你的 Harness 想象成一个这样跑的驱动程序伪代码展示全貌安装消息 [系统提示 用户任务] 循环: 响应 调用模型(消息) 如果 响应 只要文字、不想调用任何工具: 打印最终答案; 退出循环 # 模型说我想好了 否则: # 模型想调用工具 从响应里解析出工具名和参数 执行工具, 拿到结果 把[工具名, 参数, 结果]作为新消息追加进 messages # 回到循环顶部, 带着新信息重新问模型这个骨架就是后面第 8 章 DeepPilot v0.3 要用真实代码实现的东西。第 8 章第 35 节会给你一个 50 行的最小可用版本现在先在心里种下这个图景┌────────────────────────────────────────────────────────────┐ │ Agent Loop (ReAct 循环) │ │ │ │ ┌──────────────┐ │ │ │ 组装 messages │ │ │ └──────┬───────┘ │ │ ▼ │ │ ┌──────────────┐ ┌──────────────────────────────┐ │ │ │ 调用 LLM │────▶│ 响应里带了 tool_calls 吗 │ │ │ └──────┬───────┘ └──────────────┬───────────────┘ │ │ │ │ 带了 │ │ │ ▼ │ │ │ ┌──────────────────┐ │ │ │ │ 执行工具(ActObs) │ │ │ │ └────────┬─────────┘ │ │ │ │ 结果回填 │ │ └──────────────┬──────────────┘ │ │ ▼ │ │ ┌──────────────────────┐ │ │ │ 没带 → 输出最终答案 │ │ │ └──────────────────────┘ │ └────────────────────────────────────────────────────────────┘这就是 Agent 的心脏。前半段组装消息→调 LLM→看有没有 tool_calls→执行→回填→再组装——这套循环每转一圈模型就多想一步、多做一步。转几圈一个复杂任务就完成了。ReAct 与 Chain-of-Thought 的区别很多人把 ReAct 和 Chain-of-Thought思维链CoT搞混。两者的核心区别一句话就能说清维度Chain-of-Thought (CoT)ReAct本质只想不做边想边做外部信息不接触通过 Action 主动获取幻觉风险高全凭记忆低能用 Obs 纠偏适用场景纯粹的逻辑推理数学题需要查外部世界的任务产物一串思考文字思考 行动 观察结果用一个比喻收尾CoT 是让模型在自己脑子里演一场独角戏ReAct 是让它上台跟真实世界搭戏。Agent 需要的是后者——因为 Agent 的本质就是跟外部世界互动。小结ReAct 推理 行动交替循环Thought想→ Action做→ Observation看结果模型靠这个舞步一步步逼近目标。单次问答撑不起 Agent真正的能力在循环——每圈带着新信息重新想。模型不需要真的做它只需要说要做什么执行交给 Harness结果回填给模型。纯提示词就能模拟 ReAct用 search(“xxx”) 假装调用DeepSeek 会自己走完 Thought/Act/Observe/Answer 流程。Agent Loop 是所有 Agent 的心跳第 8 章 v0.3 会用 50 行代码把它变成现实。下节预告ReAct 循环里模型怎么说要做什么靠的是——tool_calls这个 JSON 结构。下一节我们解剖功能调用协议Function Callingtools 参数怎么写、tool_calls 响应怎么解析、JSON 之美到底美在哪。这是让模型出手的那只手。如果觉得本文对你有帮助欢迎点赞、收藏、关注三连本系列持续更新中关注不迷路~