一、先搞懂:ZeroShot_ReAct 到底是什么?

首先要明确两个核心概念的结合——ZeroShot(零样本)与ReAct(推理+行动),二者结合才构成了这个Agent的强大能力:

1. ReAct:让AI像人一样“思考+行动”

ReAct是一种大模型推理框架,核心逻辑源于人类解决问题的习惯:先思考(Thought),再行动(Action),根据行动结果(Observation)再调整思考,循环往复直到得出答案。这种框架打破了“大模型只做文本生成”的局限,让AI具备了“主动调用外部工具”的能力,而不是单纯依赖自身知识库回答问题。

比如面对“现在几点了”这个问题,AI不会凭空猜测,而是会思考“我需要获取当前时间,这需要调用专门的工具”,然后执行调用操作,拿到结果后再整理成最终答案——这就是ReAct的核心价值:让推理与行动协同,解决大模型“不会实时交互、不会计算”的痛点。

2. ZeroShot:无需训练,即插即用

ZeroShot(零样本)则解决了“使用门槛”的问题。传统Agent可能需要提前准备大量训练样本,告诉AI“什么场景用什么工具”,而ZeroShot_ReAct Agent完全不需要——它仅通过工具的描述信息,就能自主判断“当前问题是否需要调用工具、调用哪个工具、如何传递参数”。

简单来说,你只需要告诉Agent“有一个工具能获取当前时间,无需参数”,它就能在遇到“查询时间”的问题时,自动调用这个工具;遇到“数学计算”的问题时,自动匹配计算工具——这就是它最便捷的地方:无需训练,配置好工具和提示词,就能直接使用。

ZeroShot_ReAct 核心优势总结

  • 零样本适配:无需训练样本,仅通过工具描述即可实现工具调用决策,降低开发成本;

  • 推理透明:全程遵循“思考-行动-观察”的流程,可清晰追溯AI的决策逻辑,便于调试;

  • 灵活扩展:新增工具时,只需添加工具描述和实现逻辑,无需修改Agent核心代码;

  • 兼容性强:可适配各类兼容OpenAI API的大模型,无论是在线模型还是本地部署的模型(如Qwen、DeepSeek等)都能无缝对接。

二、实战拆解:ZeroShot_ReAct Agent 实现步骤

结合本次实战案例,我们搭建的Agent能实现两个核心功能:获取当前系统时间、执行数学表达式计算。整个实现过程分为4个核心步骤,逻辑清晰,可直接复用思路扩展更多工具。

步骤1:配置大模型(LLM)—— Agent的“大脑”

大模型是ZeroShot_ReAct Agent的核心,负责“思考决策”:判断是否需要调用工具、调用哪个工具、如何处理工具返回结果。本次实战选用了本地部署的Qwen3.5模型,通过兼容OpenAI API的方式接入LangChain。

核心配置思路:只需指定模型的API密钥、部署地址、模型名称,以及温度(temperature)和最大令牌数(max_tokens)——温度越低,AI的决策越稳定,避免随机猜测;最大令牌数则限制单次输出的长度,防止冗余。

这里的关键的是:只要模型兼容OpenAI API,无论你用的是在线模型(如GPT、DeepSeek)还是本地部署的模型(如Ollama部署的Qwen、Llama),都能直接替换使用,无需修改后续核心逻辑。

步骤2:定义工具—— Agent的“手脚”

工具是Agent与外部交互的载体,也是ZeroShot_ReAct实现“行动”的核心。每个工具都需要明确三个关键信息:工具名称、工具功能(函数实现)、工具描述——这三个信息,尤其是工具描述,直接决定了AI能否正确判断何时调用该工具。

本次实战定义了两个工具,思路可直接复用:

  • 时间工具:负责获取当前系统时间,无需输入参数,工具描述需明确“无需参数”,避免AI传递多余信息;

  • 计算工具:负责执行数学表达式计算,支持加减乘除和括号,工具描述需明确支持的表达式类型,让AI知道该工具能解决什么问题、需要传递什么格式的输入。

这里有一个细节:工具的描述必须简洁、准确,避免模糊表述。因为ZeroShot_ReAct Agent正是通过解析工具描述,来判断“当前问题是否需要调用该工具”——描述越清晰,AI的决策越准确,减少调用错误。同时,工具的函数实现需考虑安全性,比如计算工具需限制可执行的函数,避免恶意代码注入。

步骤3:自定义ReAct提示模板—— Agent的“行为准则”

提示模板(Prompt)是ZeroShot_ReAct Agent的“规则手册”,核心作用是告诉AI“如何思考、如何输出、如何调用工具”。因为大模型本身并不知道“ReAct流程”,也不知道“如何规范调用工具”,需要通过提示模板来约束其行为。

本次实战的提示模板,重点做了两个核心约束(也是ZeroShot_ReAct能正常工作的关键):

  1. 格式约束:明确规定“需要调用工具”和“无需调用工具”的输出格式,比如调用工具时必须按照“思考-行动-输入”的三行格式输出,不能添加任何多余文字,确保Agent能正确解析AI的输出;

  2. 工具约束:明确告知AI可用的工具名称和工具功能,并且强调“工具名称必须完全匹配,区分大小写”,避免AI因名称错误导致调用失败。

此外,提示模板中还预留了“历史执行记录”的位置,用于存储AI的思考、行动和观察记录,让AI能根据上一步的结果调整下一步的决策——这正是ReAct框架“循环推理”的核心实现。

步骤4:创建Agent和执行器—— 让Agent“动起来”

有了“大脑”(大模型)、“手脚”(工具)和“行为准则”(提示模板),就可以将三者组装成完整的ZeroShot_ReAct Agent,再通过执行器(AgentExecutor)来运行任务。

核心思路:使用LangChain提供的create_react_agent方法,将大模型、工具、提示模板整合,生成Agent;再通过AgentExecutor来控制Agent的执行流程,比如设置最大迭代次数(防止死循环)、开启详细日志(便于调试)、自动处理解析错误(提升稳定性)。

执行器的作用相当于“管家”,负责调度Agent的思考和行动,确保整个流程有序进行:接收用户问题 → Agent思考决策 → 调用工具(如有) → 处理工具返回结果 → 输出最终答案。

三、关键细节与避坑指南

在搭建ZeroShot_ReAct Agent的过程中,有几个细节直接影响Agent的稳定性和准确性,新手很容易踩坑,这里重点提醒:

  • 工具描述要精准:避免模糊表述,比如“计算工具”不能只写“能计算”,要明确支持的运算类型、输入格式,否则AI可能无法判断何时调用;

  • 格式约束要严格:AI的输出格式必须和提示模板中规定的一致,否则执行器无法解析,会导致调用失败——这也是为什么提示模板中要强调“不要添加任何额外文字”;

  • 大模型选择要适配:建议选择推理能力较强的模型,比如Qwen3.5、DeepSeek等,避免因模型推理能力不足,导致无法正确判断是否需要调用工具;

  • 安全性要考虑:如果工具涉及外部调用或代码执行(如计算工具),需做好安全防护,比如限制可执行的函数、过滤危险输入,避免恶意攻击。

四、总结与扩展方向

本次实战搭建的ZeroShot_ReAct Agent,虽然功能简单,但已经覆盖了核心实现逻辑——它的本质就是“通过提示模板约束大模型,让大模型根据工具描述,自主完成‘思考-行动-观察’的循环,实现零样本工具调用”。

对比传统的工具调用方式,ZeroShot_ReAct的优势在于“灵活、低成本”:无需训练样本,新增工具时只需添加工具描述和实现逻辑,就能快速适配新的需求;而ReAct框架则让AI的决策过程更加透明,便于调试和优化,这也是其在企业智能决策、自动化流程等场景中广泛应用的原因之一。

后续扩展方向也很明确:

  • 扩展工具:新增天气查询、知识库检索、文件读取等工具,实现更复杂的任务;

  • 优化提示模板:调整思考逻辑的描述,提升AI的决策准确性;

  • 对接更多模型:尝试接入不同的大模型,对比其在ZeroShot_ReAct场景下的表现;

  • 增加记忆功能:结合LangChain的记忆组件,让Agent能记住历史对话,实现多轮交互下的工具调用。

ZeroShot_ReAct Agent是LangChain Agent体系中最基础也最实用的方案,掌握它的实现思路,能为后续搭建更复杂的智能Agent(如多Agent协同、带记忆的Agent)打下坚实基础。

如果觉得本文对你有帮助,欢迎点赞、收藏,后续会持续分享LangChain实战技巧,一起玩转大模型应用开发~

代码实现:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

99

100

101

102

103

104

105

106

107

108

109

110

111

112

113

114

115

116

117

118

119

120

121

import os

from dotenv import load_dotenv

from langchain.agents import AgentExecutor, create_react_agent

from langchain_core.tools import Tool

from langchain_openai import ChatOpenAI

from langchain_core.prompts import PromptTemplate  # ← 用于自定义 prompt

# 加载环境变量

load_dotenv()

# ========================

# 1. 配置 LLM(Ollama 兼容 OpenAI API)

# ========================

DEEPSEEK_API_KEY = "123"  # 替换为实际的 API Key

llm = ChatOpenAI(

    api_key=DEEPSEEK_API_KEY,

    base_url="http://192.168.0.100:8085/v1",

    model="qwen3.5-27b-awq",

    temperature=0.3,

    max_tokens=1024,

)

# ========================

# 2. 定义工具

# ========================

def get_current_time(*args, **kwargs):

    from datetime import datetime

    current_time = datetime.now().strftime("%Y年%m月%d日 %H:%M:%S")

    return f"当前时间:{current_time}"

def calculate_math_expression(expression: str):

    try:

        # 构建安全的白名单内置函数

        safe_funcs = {}

        for func_name in ("abs""round""min""max""pow"):

            if hasattr(__builtins__, func_name):

                safe_funcs[func_name] = getattr(__builtins__, func_name)

        # 执行安全计算

        result = eval(expression, {"__builtins__": {}}, safe_funcs)

        return f"数学表达式计算结果:{expression} = {result}"

    except Exception as e:

        return f"计算失败,错误信息:{str(e)}"

tools = [

    Tool(

        name="GetCurrentTime",

        func=get_current_time,

        description="获取当前系统时间,无需任何输入参数"

    ),

    Tool(

        name="CalculateMathExpression",

        func=calculate_math_expression,

        description="计算一个数学表达式,例如 '100 * (25 + 15) / 4 - 80',仅支持 + - * / 和括号"

    )

]

# ========================

# 3. 自定义 ReAct 提示模板(中文 + 严格格式约束)

# ========================

react_prompt_template = """你是一个智能助手,必须严格遵守以下交互协议:

## 规则

1. 如果需要使用工具,请**严格按照以下三行格式输出**,不要添加任何额外文字、标点、说明或自然语言:

Thought: 我需要使用工具来解决问题。

Action: 工具名称

Action Input: 工具输入内容

2. 如果不需要工具,直接输出:

Thought: 我可以直接回答。

Final Answer: 你的最终答案

## 可用工具

{tools}

## 合法工具名称(必须完全匹配,区分大小写):

{tool_names}

## 用户问题

{input}

## 历史执行记录(如有)

{agent_scratchpad}

"""

# 创建 PromptTemplate,确保包含所有必要变量

prompt = PromptTemplate(

    input_variables=["tools""tool_names""input""agent_scratchpad"],

    template=react_prompt_template

)

# ========================

# 4. 创建 Agent 和执行器

# ========================

agent = create_react_agent(

    llm=llm,

    tools=tools,

    prompt=prompt

)

agent_executor = AgentExecutor(

    agent=agent,

    tools=tools,

    verbose=True,

    handle_parsing_errors=True,   # 自动处理解析错误并重试

    max_iterations=5,             # 防止死循环

)

# ========================

# 5. 执行任务

# ========================

if __name__ == "__main__":

    print("===== 任务1:获取当前时间 =====")

    agent_executor.invoke({"input""请告诉我现在的时间是多少?"})

    print("\n" + "=" * 50 + "\n")

    print("===== 任务2:数学计算 =====")

    agent_executor.invoke({"input""请帮我计算 100 * (25 + 15) / 4 - 80 的结果是多少?"})

结果输出:

===== 任务1:获取当前时间 =====


> Entering new AgentExecutor chain...
写。
</think>

Thought: 我需要使用工具来解决问题。
Action: GetCurrentTime
Action Input:当前时间:2026年04月07日 16:49:28案。
</think>

Thought: 我可以直接回答。
Final Answer: 当前时间是2026年04月07日 16:49:28。

> Finished chain.

==================================================

===== 任务2:数学计算 =====


> Entering new AgentExecutor chain...
0'
</think>

Thought: 我需要使用工具来解决问题。
Action: CalculateMathExpression
Action Input: 100 * (25 + 15) / 4 - 80数学表达式计算结果:100 * (25 + 15) / 4 - 80 = 920.0题。
</think>

Logo

汇聚全球AI编程工具,助力开发者即刻编程。

更多推荐