Function Calling
# 定义工具列表
tools = [
{
"type": "function",
"function": {
"name": "get_current_weather",
"description": "当你想查询指定城市的天气时非常有用。",
"parameters": {
"type": "object",
"properties": {
"location": {
"type": "string",
"description": "城市或县区,比如北京市、杭州市、余杭区等。",
}
},
"required": ["location"],
},
},
},
]
# 模拟天气查询工具
def get_current_weather(arguments):
weather_conditions = ["晴天", "多云", "雨天"]
random_weather = random.choice(weather_conditions)
location = arguments["location"]
return f"{location}今天是{random_weather}。"
# 封装模型响应函数
def get_response(messages):
completion = client.chat.completions.create(
model="qwen-plus",
messages=messages,
tools=tools,
)
return completion
先思考
首先我们已经了解过 Function Calling 的过程,那么用户提问“我昨天买的会员怎么没到账?”,难道是通过一个提示词中写“先查询用户昨天是否购买会员,可以调用xxx,如果昨天购买了,那么再看用户当前是否是会员可以调用xxx,如果不是xxx”来完成吗?还是说完全交给 LLM 判断?
纯LLM流程上完全自由不可预测,且合规性也不符合高安全性(金融级)的要求,要求可审计可观测性
你会怎么设计?
智能体 = 大语言模型(LLM) + 观察 + 思考 + 行动 + 记忆
- 大语言模型(LLM):LLM作为智能体的“大脑”部分,使其能够处理信息,从交互中学习,做出决策并执行行动。
- 观察:这是智能体的感知机制,使其能够感知其环境。智能体可能会接收来自另一个智能体(工具、MCP)的文本消息、来自监视摄像头的视觉数据或来自客户服务录音的音频等一系列信号。这些观察构成了所有后续行动的基础。
- 思考:思考过程涉及分析观察结果和记忆内容并考虑可能的行动。这是智能体内部的决策过程,其可能由LLM进行驱动(可以混合)。
- 行动:这些是智能体对其思考和观察的显式响应。行动可以是利用 LLM 生成代码,或是手动预定义的操作,如阅读本地文件。此外,智能体还可以执行使用工具的操作,包括在互联网上搜索天气,使用计算器进行数学计算等。
- 记忆:智能体的记忆存储过去的经验。这对学习至关重要,因为它允许智能体参考先前的结果并据此调整未来的行动。
智能体示例
帮我基于python3.11实现一个可生成100个随机偶数的脚本。
要求:
代码优雅,无性能问题;
脚本通过main函数启动
多智能体 = 智能体 + 环境 + 标准流程(SOP) + 通信 + 经济
- 智能体:在上面单独定义的基础上,在多智能体系统中的智能体协同工作,每个智能体都具备独特有的LLM、观察、思考、行动和记忆。
- 环境:环境是智能体生存和互动的公共场所。智能体从环境中观察到重要信息,并发布行动的输出结果以供其他智能体使用。(实验室内可以做实验,可以观察到实验成果)
- 标准流程(SOP)/状态机:这些是管理智能体行动和交互的既定程序,确保系统内部的有序和高效运作。例如,在汽车制造的SOP中,一个智能体焊接汽车零件,而另一个安装电缆,保持装配线的有序运作。
- 通信:通信是智能体之间信息交流的过程。它对于系统内的协作、谈判和竞争至关重要。
- 经济:这指的是多智能体环境中的价值交换系统,决定资源分配和任务优先级。(各个子任务)
plan.md 意图识别,生成计划
OTA:Observe/Observation(观察)+ think/thought(思考)+ Act/Action(行动)。
ReAct*(Reason + Act)*:可能是一个循环反复的过程,计划规划后开始 Act 即执行阶段,随后 Observe 观察分析结果,然后根据分析的结果进行思考决策,决策出下一步。
观察分析:专门判断异常的 Agent,混合模式,可静态代码判断(如响应码、退出状态码等)+ LLM判断(响应输出body、异常堆栈)
持久化
(印证开头思考,为什么不单靠LLM)用户需求越复杂,任务环节越多越重要,并不是仅靠某单一大模型能解决的事
Q:当前模型能力可能不足,如果伴随模型迭代,更强大的模型能完成所有事?
A:混合状态机
动态Agent
何为状态机?
状态机(State Machine)是计算机科学中一种数学模型,用于描述系统在不同状态之间转换的行为。它的核心思想是:系统在任何时刻都处于一个明确的状态,外部事件触发状态转换,并执行相应动作。
思考做一件事哪些事情是动态哪些是固定的
“我想做一个关于su7的ppt”
固定:资料搜集(文字+图片)→ ppt文案提取 → 制作每一页 → 合并所有页 → 演示
非固定:
- 如果没有合适图片,需要自行画图
整体大方向(层与层之间的)执行流程由大模型推导出Plan,具体业务线或细小部分程序代码控制(部分 状态机/工作流引擎)同时决策部分可通过LLM实现动态决策
用户积分
“我昨天发了视频,但积分没加上?”、“我昨天积分不太对”
上图蓝色流程可能是某个子 Agent 中的流程,如“查视频发布 Agent”,“用户积分计算 Agent(先查询积分明细与次数,再查询是否会员)”具体调用哪些大 Agent 由模型推断出来。
“我昨天买的会员怎么没到账?”
子Agent(1->2->3):
- 核实是否购买会员 – “查询会员订单Agent”
- 核实用户当前会员状态 – “查询用户会员状态与有效期Agent”
- 核实订单商品类型与会员所续周期是否一致 – “验证Agent”
模型总结结果
(印证开头思考,为什么不单靠LLM)既然LLM很强大,为什么还需要引入状态机?
状态机是将复杂流程分解为可控状态转换的架构模式。在Agent系统中:
- 不是替代LLM,而是为LLM提供安全执行框架
- 不是限制灵活性,而是将灵活性控制在预定义边界内(模型幻觉、指令忽略)
- 不是过时技术,而是现代Agent系统的基石架构
对于业务,状态机确保主流程100%可控,而LLM可以在每个状态内部处理语义理解、异常分析等动态决策,实现安全与智能的最佳平衡。
如果仅决策依靠LLM,为什么不自己写if else?
- ✅意图识别需要LLM;
case判断需要LLM,“我昨天发了视频,但积分没加上?”、“我昨天积分不太对” - ✅内容提取需要LLM;(如“我想知道北京的天气”,提取出“北京”的参数以便工具调用)
❌字符串正则匹配 - ✅内容整合需要LLM;
❌纯字符串或结果拼接 - ✅代码运行结果,自动异常堆栈分析;
❌程序无法自动分析出可能原因
这是一个Agent吗?
查询天气FunctionCalling
from openai import OpenAI
from datetime import datetime
import json
import os
import random
# 初始化客户端
client = OpenAI(
# 若没有配置环境变量,请用阿里云百炼API Key将下行替换为:api_key="sk-xxx",
# 新加坡和北京地域的API Key不同。获取API Key:https://help.aliyun.com/zh/model-studio/get-api-key
api_key=os.getenv("DASHSCOPE_API_KEY"),
# 以下是北京地域base_url,如果使用新加坡地域的模型,需要将base_url替换为:https://dashscope-intl.aliyuncs.com/compatible-mode/v1
base_url="https://dashscope.aliyuncs.com/compatible-mode/v1",
)
# 模拟用户问题
USER_QUESTION = "北京天气咋样"
# 定义工具列表
tools = [
{
"type": "function",
"function": {
"name": "get_current_weather",
"description": "当你想查询指定城市的天气时非常有用。",
"parameters": {
"type": "object",
"properties": {
"location": {
"type": "string",
"description": "城市或县区,比如北京市、杭州市、余杭区等。",
}
},
"required": ["location"],
},
},
},
]
# 模拟天气查询工具
def get_current_weather(arguments):
weather_conditions = ["晴天", "多云", "雨天"]
random_weather = random.choice(weather_conditions)
location = arguments["location"]
return f"{location}今天是{random_weather}。"
# 封装模型响应函数
def get_response(messages):
completion = client.chat.completions.create(
model="qwen-plus",
messages=messages,
tools=tools,
)
return completion
messages = [{"role": "user", "content": USER_QUESTION}]
response = get_response(messages)
assistant_output = response.choices[0].message
if assistant_output.content is None:
assistant_output.content = ""
messages.append(assistant_output)
# 如果不需要调用工具,直接输出内容
if assistant_output.tool_calls is None:
print(f"无需调用天气查询工具,直接回复:{assistant_output.content}")
else:
# 进入工具调用循环
while assistant_output.tool_calls is not None:
tool_call = assistant_output.tool_calls[0]
tool_call_id = tool_call.id
func_name = tool_call.function.name
arguments = json.loads(tool_call.function.arguments)
print(f"正在调用工具 [{func_name}],参数:{arguments}")
# 执行工具
tool_result = get_current_weather(arguments)
# 构造工具返回信息
tool_message = {
"role": "tool",
"tool_call_id": tool_call_id,
"content": tool_result, # 保持原始工具输出
}
print(f"工具返回:{tool_message['content']}")
messages.append(tool_message)
# 再次调用模型,获取总结后的自然语言回复
response = get_response(messages)
assistant_output = response.choices[0].message
if assistant_output.content is None:
assistant_output.content = ""
messages.append(assistant_output)
print(f"助手最终回复:{assistant_output.content}")
这段代码 可以被视作一个最简形式的“Agent”雏形,但严格来说,它属于 Function Calling(函数调用)驱动的单步工具调用流程,尚未达到典型 LLM Agent 的完整能力。我们可以从 Agent 的核心特征出发进行分析:
✅ 它具备的部分 Agent 特征
- 感知(Perception)
- 接收用户输入(
USER_QUESTION = "北京天气咋样")。
- 接收用户输入(
- 决策(Reasoning)
- 大模型(Qwen-Plus)根据问题判断是否需要调用工具(
get_current_weather)。
- 大模型(Qwen-Plus)根据问题判断是否需要调用工具(
- 行动(Action)
- 调用外部“工具”(虽然是模拟的
get_current_weather函数)获取信息。
- 调用外部“工具”(虽然是模拟的
- 反馈与迭代(Reflection / Iteration)
- 将工具返回结果注入对话上下文,并再次调用模型生成最终自然语言回复。
这符合 ReAct(Reason + Act)范式 的基本结构,是当前主流 Agent 架构的基础。
参考:Yao et al., ReAct: Synergizing Reasoning and Acting in Language Models, ICLR 2023.
https://arxiv.org/abs/2210.03629
❌ 它缺失的典型 Agent 能力
- 多工具支持与动态选择
- 当前只注册了一个工具。真实 Agent 应能从多个工具中按需选择(如查天气、查日历、发邮件等)。
- 多轮工具调用(Multi-step Tool Use)
- 仅支持单次工具调用(虽然有 while 循环,但实际只处理第一个
tool_call)。若模型返回多个并行工具调用,此代码无法正确处理。
- 仅支持单次工具调用(虽然有 while 循环,但实际只处理第一个
- 状态管理与记忆(Memory)
- 没有长期记忆、会话历史压缩或上下文摘要机制。
- 目标导向与规划(Planning)
- 无法分解复杂任务(如“帮我订一张明天从北京到上海的 cheapest 机票”),缺乏子目标拆解和执行顺序规划。
- 错误恢复与重试机制
- 工具失败时无 fallback 策略(如重试、换工具、向用户澄清)。
- 安全与权限控制
- 未考虑工具调用的安全边界(例如防止 LLM 调用危险操作)。
结论
- 学术/工程上:这是一个 基于 Function Calling 的简单 Tool-Using Agent 原型(Minimal Agent),常用于演示或教学。
- 工业级 Agent 系统(如 LangChain Agent、LlamaIndex ReActAgent、AutoGen、OpenDevin)通常包含上述缺失的能力模块。
工业级成熟 Agent




发表评论