Function Call 和 Agent 工具调用到底有什么区别?
本文介绍了LLM Function Call和Agent Tool Use的区别,以及如何写一个Demo。
文章目录
前言:为什么我会学这个问题
之前我写了个 AI 助手,让它帮我查天气、调接口,它时而正常时而发疯——有时候返回纯文本,有时候乱格式,有时候干脆不调用工具。后来我发现问题不在模型,在于我混淆了 Function Call 和 Agent 工具调用 这两个完全不同机制。这篇就来把它们彻底讲清楚。
前文关联:这是《AI Agent 工程实践》系列的开篇,我们从最基础的概念区分开始。
一、问题背景
做 AI 项目时,大家都在说"让 AI 调用工具",但实现方式分两种:
- Function Call(函数调用):模型原生能力,结构化输出,固定格式
- Agent 工具调用(Tool Use by Agent):Agent 框架的能力,动态决策,可编排
大多数教程把它们混为一谈,导致代码写得四不像。
二、核心概念
Function Call 是什么?
Function Call 是 LLM 的内置能力。模型收到用户问题后,直接在响应中输出一个结构化的函数调用请求,格式类似:
{
"name": "get_weather",
"arguments": {"city": "北京"}
}
这个过程模型一次输出完成,不存在"思考要不要调用"的环节。

Agent 工具调用是什么?
Agent 工具调用是 Agent 框架(比如 LangChain、LangGraph)里的能力。Agent 会:
- 思考(Think):模型输出"我应该调用工具"
- 决定调用哪个(Action):从多个工具中选择
- 执行(Execute):调用工具
- 观察结果(Observation):把结果传回模型
- 再次思考:模型决定下一步
这是一个循环,不是一次性的。

核心区别
| Function Call | Agent 工具调用 | |
|---|---|---|
| 本质 | 模型原生能力 | Agent 框架编排 |
| 决策 | 一次性决策 | 循环决策 |
| 工具数量 | 通常单工具 | 多工具可选 |
| 灵活性 | 低,格式固定 | 高,可编排 |
| 适用场景 | 简单、结构化任务 | 复杂、多步骤任务 |
三、错误理解 / 常见误区
误区1:Function Call 就是 Agent
错。Function Call 只是让模型输出结构化 JSON,不包含执行逻辑。你还得自己解析 JSON、调用函数、把结果传回去。
误区2:Agent 必须用 Function Call
错。Agent 可以用 Function Call,也可以用 prompt engineering(比如在思维链里写"当你需要查天气时,直接在回答里插入 TOOL_CALL: get_weather")。Function Call 只是实现工具调用的一种方式。
误区3:Function Call 比 Agent 简单,所以功能也弱
不完全对。Function Call 的"简单"指的是调用方式简单,不代表能力弱。很多复杂任务可以用多工具的 Function Call 实现。
误区4:Agent 调用工具后模型就完成了
错。工具返回结果后,Agent 会把这个结果再传回模型,让模型继续决定下一步。这就是 Agent 的"循环"机制。
四、正确实现思路
Function Call 实现步骤
- 定义工具 schema(符合 OpenAI 格式)
- 把工具 schema 和用户问题一起发给模型
- 解析模型返回的函数调用
- 执行实际函数
- 把函数结果和原问题一起发回模型,让它组织最终回答
# 伪代码
tools = [
{
"type": "function",
"function": {
"name": "get_weather",
"description": "获取城市天气",
"parameters": {
"type": "object",
"properties": {"city": {"type": "string"}}
}
}
}
]
response = openai.chat.completions.create(
model="gpt-4",
messages=[{"role": "user", "content": "北京天气怎么样?"}],
tools=tools
)
# 解析 Function Call
tool_calls = response.choices[0].message.tool_calls
if tool_calls:
for call in tool_calls:
if call.function.name == "get_weather":
result = get_weather(call.function.arguments["city"])
# 把结果发回模型,获取最终回答
final = openai.chat.completions.create(
model="gpt-4",
messages=[
{"role": "user", "content": "北京天气怎么样?"},
response.choices[0].message,
{"role": "tool", "tool_call_id": call.id, "content": result}
]
)
Agent 工具调用实现步骤
- 定义 Agent Prompt(包含工具描述、决策逻辑)
- Agent 接收用户问题,输出思考 + 工具调用
- 执行工具,把结果返回给 Agent
- Agent 继续思考,直到决定不再调用工具
- 返回最终答案
# LangChain Agent 伪代码
from langchain.agents import AgentExecutor, create_openai_functions_agent
from langchain.tools import tool
@tool
def get_weather(city: str):
"""获取城市天气"""
return f"{city}今天晴,25度"
tools = [get_weather]
prompt = """你是一个助手。
当你需要查天气时,调用 get_weather 工具。
其他情况直接回答。"""
agent = create_openai_functions_agent(llm, tools, prompt)
executor = AgentExecutor(agent=agent, tools=tools)
result = executor.invoke({"input": "北京天气怎么样?"})
# Agent 会自动:思考 -> 调用工具 -> 拿到结果 -> 再思考 -> 返回答案
五、代码示例
Function Call 完整示例(Python)
import json
from openai import OpenAI
client = OpenAI(api_key="your-api-key")
# 定义工具
tools = [
{
"type": "function",
"function": {
"name": "get_weather",
"description": "获取指定城市的天气信息",
"parameters": {
"type": "object",
"properties": {
"city": {
"type": "string",
"description": "城市名称,如:北京、上海"
}
},
"required": ["city"]
}
}
}
]
def get_weather(city: str) -> str:
"""模拟天气查询"""
weather_data = {"北京": "晴,25°C", "上海": "雨,18°C"}
return weather_data.get(city, "未知")
def call_function(name: str, args: dict) -> str:
"""执行函数调用"""
if name == "get_weather":
return get_weather(**args)
return "未知函数"
# 第一轮:用户提问,模型决定调用工具
messages = [{"role": "user", "content": "北京今天天气怎么样?"}]
response = client.chat.completions.create(
model="gpt-4o-mini",
messages=messages,
tools=tools,
tool_choice="auto"
)
assistant_msg = response.choices[0].message
print("模型响应:", assistant_msg)
# 解析并执行函数调用
if assistant_msg.tool_calls:
tool_call = assistant_msg.tool_calls[0]
func_name = tool_call.function.name
func_args = json.loads(tool_call.function.arguments)
print(f"\n执行函数: {func_name}({func_args})")
func_result = call_function(func_name, func_args)
print(f"函数返回: {func_result}")
# 第二轮:把函数结果发回模型,获取最终回答
messages.append(assistant_msg)
messages.append({
"role": "tool",
"tool_call_id": tool_call.id,
"content": func_result
})
final_response = client.chat.completions.create(
model="gpt-4o-mini",
messages=messages
)
print("\n最终回答:", final_response.choices[0].message.content)
六、运行结果 / 流程图
运行结果:
模型响应: ChatCompletionMessage(content=None, tool_calls=[ChatCompletionMessageToolCall(id='...', function=Function(arguments='{"city": "北京"}', name='get_weather'), type='function')])
执行函数: get_weather({'city': '北京'})
函数返回: 北京今天晴,25°C
最终回答: 北京今天天气晴朗,气温约25摄氏度,适合外出活动。

七、项目中怎么用
实际场景:
- 简单任务(查天气、算数学):用 Function Call 就够了,一次调用搞定
- 复杂任务(多步骤分析、多工具组合):用 Agent 框架
最佳实践:
- 不要过度设计:能 Function Call 解决就别上 Agent
- 工具描述要清晰:模型靠 description 决定调用哪个工具
- 错误处理:工具执行可能失败,要有重试和降级方案
- 避免循环调用:Agent 里设置 max_iterations 防止死循环
系列关联:本文介绍了 Agent 工具调用的基础。下一篇《LangGraph 中 State、Node、Edge 是怎么协作的?》将深入讲 Agent 的核心组件,理解这三个概念是理解 LangGraph 工作原理的基础。
八、总结 + 下篇预告
核心要点:
- Function Call 是模型原生能力,一次性输出结构化函数调用
- Agent 工具调用是循环过程:思考→决策→执行→观察→再思考
- Function Call 适合简单单步任务,Agent 适合复杂多步骤任务
- 两者不是替代关系,是不同场景的选择
下篇预告:下一篇我们将探讨《LangGraph 中 State、Node、Edge 是怎么协作的?》,深入理解 LangGraph 的三大核心概念,理解它们如何配合实现复杂的 Agent 流程。也是我个人学习的记录。
延伸阅读:
更多推荐

所有评论(0)