初识智能体
一句话
智能体是通过传感器感知环境,自主通过执行器采取行动以达成特定目标的实体。
什么时候翻这页
当你需要理解智能体的基本概念、类型、工作原理以及如何构建一个简单的智能体时。
核心概念
- 智能体(Agent):通过传感器(Sensors)感知环境(Environment),自主通过执行器(Actuators)采取行动(Action)以达成特定目标的实体。
- 自主性(Autonomy):智能体基于感知和内部状态进行独立决策的能力。
- 传感器(Sensors):智能体感知环境的工具,如摄像头、麦克风、API等。
- 执行器(Actuators):智能体对环境施加影响的工具,如物理设备或虚拟工具。
- 应用程序编程接口(API):智能体与外部系统交互的接口。
- 传统智能体:大语言模型(LLM)出现前的智能体范式。
- 反射智能体(Simple Reflex Agent):基于"条件-动作"规则决策的智能体。
- 基于模型的反射智能体(Model-Based Reflex Agent):拥有内部世界模型,追踪环境中无法直接感知的方面。
- 基于目标的智能体(Goal-Based Agent):主动选择能够导向特定未来状态的行动。
- 基于效用的智能体(Utility-Based Agent):为每个可能的世界状态赋予效用值,目标是最大化期望效用。
- 学习型智能体(Learning Agent):通过与环境的互动自主学习,如强化学习(Reinforcement Learning, RL)。
- 大语言模型(LLM)智能体:由大语言模型驱动的智能体,具备规划与推理、工具使用、动态修正等能力。
- PEAS模型:描述任务环境的模型,包括性能度量(Performance)、环境(Environment)、执行器(Actuators)和传感器(Sensors)。
- 智能体循环(Agent Loop):智能体与环境交互的持续循环,包括感知(Perception)、思考(Thought)、行动(Action)和观察(Observation)。
- 交互协议(Interaction Protocol):规范智能体与环境之间信息交换的协议。
- 符号主义AI(Symbolic AI):智能源于对符号的逻辑操作。
- 亚符号主义AI(Sub-symbolic AI):知识内隐地分布在神经网络中,是从海量数据中学习到的统计模式。
- 神经符号主义AI(Neuro-Symbolic AI):融合符号主义和亚符号主义的优点,既能从数据中学习,又能进行逻辑推理。
- 反应性(Reactivity):智能体对环境刺激做出即时响应的特性。
- 规划性(Deliberation):智能体在行动前进行复杂思考和规划的特性。
- 混合式智能体(Hybrid Agents):结合反应性和规划性的智能体。
- 提示工程(Prompt Engineering):设计指令模板,指导LLM如何思考和行动。
- Workflow:对一系列任务或步骤进行预先定义的、结构化的编排。
- Agent:具备自主性的、以目标为导向的系统,能够理解环境、进行推理、制定计划,并动态采取行动。
怎么做
- 定义智能体任务环境:使用PEAS模型分析性能度量、环境、执行器和传感器。
- 构建智能体循环:实现感知-思考-行动-观察的闭环。
- 设计交互协议:规范智能体输出的Thought和Action格式。
- 实现工具调用:定义可用的工具函数,供智能体调用。
- 接入大语言模型:使用兼容OpenAI接口的客户端连接LLM服务。
- 执行行动循环:通过格式化Prompt驱动LLM进行决策,解析并执行行动,记录观察结果。
命令 / 代码速查
# 安装必要的库
pip install requests tavily-python openai
# 指令模板
AGENT_SYSTEM_PROMPT = """
你是一个智能旅行助手。你的任务是分析用户的请求,并使用可用工具一步步地解决问题。
# 可用工具:
- `get_weather(city: str)`: 查询指定城市的实时天气。
- `get_attraction(city: str, weather: str)`: 根据城市和天气搜索推荐的旅游景点。
# 输出格式要求:
你的每次回复必须严格遵循以下格式,包含一对Thought和Action:
Thought: [你的思考过程和下一步计划]
Action: [你要执行的具体行动]
Action的格式必须是以下之一:
1. 调用工具:function_name(arg_name="arg_value")
2. 结束任务:Finish[最终答案]
# 重要提示:
- 每次只输出一对Thought-Action
- Action必须在同一行,不要换行
- 当收集到足够信息可以回答用户问题时,必须使用 Action: Finish[最终答案] 格式结束
请开始吧!
"""
# 工具1:查询真实天气
import requests
def get_weather(city: str) -> str:
"""
通过调用 wttr.in API 查询真实的天气信息。
"""
url = f"https://wttr.in/{city}?format=j1"
try:
response = requests.get(url)
response.raise_for_status()
data = response.json()
current_condition = data['current_condition'][0]
weather_desc = current_condition['weatherDesc'][0]['value']
temp_c = current_condition['temp_C']
return f"{city}当前天气:{weather_desc},气温{temp_c}摄氏度"
except requests.exceptions.RequestException as e:
return f"错误:查询天气时遇到网络问题 - {e}"
except (KeyError, IndexError) as e:
return f"错误:解析天气数据失败,可能是城市名称无效 - {e}"
# 工具2:搜索并推荐旅游景点
import os
from tavily import TavilyClient
def get_attraction(city: str, weather: str) -> str:
"""
根据城市和天气,使用Tavily Search API搜索并返回优化后的景点推荐。
"""
api_key = os.environ.get("TAVILY_API_KEY")
if not api_key:
return "错误:未配置TAVILY_API_KEY环境变量。"
tavily = TavilyClient(api_key=api_key)
query = f"'{city}' 在'{weather}'天气下最值得去的旅游景点推荐及理由"
try:
response = tavily.search(query=query, search_depth="basic", include_answer=True)
if response.get("answer"):
return response["answer"]
formatted_results = []
for result in response.get("results", []):
formatted_results.append(f"- {result['title']}: {result['content']}")
if not formatted_results:
return "抱歉,没有找到相关的旅游景点推荐。"
return "根据搜索,为您找到以下信息:\n" + "\n".join(formatted_results)
except Exception as e:
return f"错误:执行Tavily搜索时出现问题 - {e}"
# 接入大语言模型
from openai import OpenAI
class OpenAICompatibleClient:
"""
一个用于调用任何兼容OpenAI接口的LLM服务的客户端。
"""
def __init__(self, model: str, api_key: str, base_url: str):
self.model = model
self.client = OpenAI(api_key=api_key, base_url=base_url)
def generate(self, prompt: str, system_prompt: str) -> str:
"""调用LLM API来生成回应。"""
print("正在调用大语言模型...")
try:
messages = [
{'role': 'system', 'content': system_prompt},
{'role': 'user', 'content': prompt}
]
response = self.client.chat.completions.create(
model=self.model,
messages=messages,
stream=False
)
answer = response.choices[0].message.content
print("大语言模型响应成功。")
return answer
except Exception as e:
print(f"调用LLM API时发生错误: {e}")
return "错误:调用语言模型服务时出错。"
# 执行行动循环
import re
# 配置LLM客户端
API_KEY = "YOUR_API_KEY"
BASE_URL = "YOUR_BASE_URL"
MODEL_ID = "YOUR_MODEL_ID"
TAVILY_API_KEY="YOUR_Tavily_KEY"
os.environ['TAVILY_API_KEY'] = "YOUR_TAVILY_API_KEY"
llm = OpenAICompatibleClient(
model=MODEL_ID,
api_key=API_KEY,
base_url=BASE_URL
)
# 初始化
user_prompt = "你好,请帮我查询一下今天北京的天气,然后根据天气推荐一个合适的旅游景点。"
prompt_history = [f"用户请求: {user_prompt}"]
print(f"用户输入: {user_prompt}\n" + "="*40)
# 运行主循环
for i in range(5): # 设置最大循环次数
print(f"--- 循环 {i+1} ---\n")
# 构建Prompt
full_prompt = "\n".join(prompt_history)
# 调用LLM进行思考
llm_output = llm.generate(full_prompt, system_prompt=AGENT_SYSTEM_PROMPT)
# 模型可能会输出多余的Thought-Action,需要截断
match = re.search(r'(Thought:.*?Action:.*?)(?=\n\s*(?:Thought:|Action:|Observation:)|\Z)', llm_output, re.DOTALL)
if match:
truncated = match.group(1).strip()
if truncated != llm_output.strip():
llm_output = truncated
print("已截断多余的 Thought-Action 对")
print(f"模型输出:\n{llm_output}\n")
prompt_history.append(llm_output)
# 解析并执行行动
action_match = re.search(r"Action: (.*)", llm_output, re.DOTALL)
if not action_match:
observation = "错误: 未能解析到 Action 字段。请确保你的回复严格遵循 'Thought: ... Action: ...' 的格式。"
observation_str = f"Observation: {observation}"
print(f"{observation_str}\n" + "="*40)
prompt_history.append(observation_str)
continue
action_str = action_match.group(1).strip()
if action_str.startswith("Finish"):
final_answer = re.match(r"Finish\[(.*)\]", action_str).group(1)
print(f"任务完成,最终答案: {final_answer}")
break
tool_name = re.search(r"(\w+)\(", action_str).group(1)
args_str = re.search(r"\((.*)\)", action_str).group(1)
kwargs = dict(re.findall(r'(\w+)="([^"]*)"', args_str))
if tool_name in available_tools:
observation = available_tools[tool_name](**kwargs)
else:
observation = f"错误:未定义的工具 '{tool_name}'"
# 记录观察结果
observation_str = f"Observation: {observation}"
print(f"{observation_str}\n" + "="*40)
prompt_history.append(observation_str)
与 Python / Claude Code 手册的联系
- Python手册中的requests库用于实现智能体的工具调用功能
- Claude Code手册中的提示工程(Prompt Engineering)概念与智能体指令模板设计密切相关
- Claude Code中的无交互模式(headless mode)与智能体的自主执行循环类似
初学者易错点
- 混淆智能体与传统程序:智能体具有自主性,能够根据环境变化调整行为,而传统程序只是执行预设指令。
- 忽视环境特性:任务环境可能是部分可观察、随机性、多智能体或序贯动态的,需要智能体具备相应能力。
- 循环控制不当:智能体循环可能陷入无限循环,需要设置最大循环次数或终止条件。
- 工具调用失败处理:未处理API调用失败、参数错误等异常情况。
- 输出格式不匹配:LLM输出格式不符合交互协议要求,导致解析失败。
相关词条
- ReAct:结合推理(Reasoning)和行动(Acting)的智能体范式
- MCP(Model Context Protocol):模型上下文协议,用于智能体与工具的交互
- LangGraph:构建高级控制流架构的框架,用于实现复杂智能体工作流
- 强化学习(Reinforcement Learning):实现学习型智能体的方法
- 提示工程(Prompt Engineering):设计有效提示的技术