当前位置: 首页 > news >正文

从0到1,构建你的第一个AI Agent:核心原理与实战指南

从0到1,构建你的第一个AI Agent:核心原理与实战指南

AI Agent 正从论文走向生产,但很多人上手就是 LangChain、AutoGPT 这类高级框架,结果往往是“会用但不理解,能跑但不可控”。如果你曾好奇:在不依赖任何框架的情况下,如何从零写出一个能推理、能调用工具、有记忆的自主智能体?这篇文章就是为你准备的。

我们将沿着“概念→设计→代码→优化”的路径,一步步构建出一个最小可行的 AI Agent,并深入理解它的骨架和灵魂。


一、先想清楚:AI Agent 到底是个什么东西

它不是单纯的“问答机器人”。我们可以用一条经典公式来定义它:

Agent = LLM + 记忆(Memory)+ 规划(Planning)+ 工具(Tools)

  • LLM:大脑,负责理解、推理和生成。
  • 记忆:分为短期记忆(对话上下文)和长期记忆(外部知识库,如向量数据库)。
  • 规划:能拆解复杂任务、自我反思、动态调整执行路径。
  • 工具:对外界施加影响的手和脚,如搜索引擎、计算器、API调用。

与传统“输入-输出”的 GPT 包装器不同,Agent 会进入一个感知-规划-行动循环
它会观察当前状态(包括历史消息和工具返回),用 LLM 进行推理,决定下一步是执行某个工具还是直接给出最终答案,反复循环直到目标完成。

这个循环的核心设计模式就是ReAct(Reasoning + Acting)——让模型交替输出“思考”和“行动”,并用标准格式将行动结构化,方便程序解析和执行。这也是我们实现时的灵魂所在。


二、动手前的核心设计:一个可扩展的 Agent 架构

让我们把需求具体化:我们要一个通用 Agent,可以配置不同的工具和系统提示,对任意问题自主拆解并调用工具。它的主循环应该是:

  1. 接收用户输入,加入短期记忆。
  2. 拼接系统提示 + 历史消息 + 可用工具列表,请求 LLM。
  3. 解析 LLM 输出:
    • 如果是最终答案,结束循环并返回结果;
    • 如果是工具调用请求,执行对应的工具,将结果作为一条新消息加入历史,返回步骤2。
  4. 设置最大循环次数,防止无限循环或过度消耗。

我们将用 Python 实现,调用 OpenAI 的原生 Function Calling能力(因为它极大地降低了解析成本),但原理完全适用于任何支持指令遵循的开源模型(可通过约束 JSON 输出来模拟)。


三、从零编写代码:最小可行 Agent

1. 工具系统:让 Agent 长出双手

首先要定义一种统一的工具接口。每个工具需要有名称、描述和符合 JSON Schema 的参数定义。

importjsonclassTool:def__init__(self,name,description,func,parameters):self.name=name self.description=description self.func=func self.parameters=parameters# JSON Schema properties dictdefto_openai_function(self):return{"type":"function","function":{"name":self.name,"description":self.description,"parameters":{"type":"object","properties":self.parameters,"required":list(self.parameters.keys())}}}defexecute(self,**kwargs):returnself.func(**kwargs)

我们来实现一个简单的计算器工具和一个模拟搜索工具作为例子:

defcalculator(expression:str):# 安全起见,仅允许基础运算;生产环境必须沙箱化allowed_chars=set("0123456789+-*/().% ")ifnotset(expression).issubset(allowed_chars):return"Error: 表达式含非法字符"try:returnstr(eval(expression))exceptExceptionase:returnf"计算错误:{e}"defweb_search(query:str):# 模拟搜索结果,实际可接入 SerpAPI / Tavily 等returnf"关于'{query}'的搜索结果:这里是一些模拟摘要..."tools=[Tool(name="calculator",description="执行数学计算,输入一个数学表达式字符串",func=calculator,parameters={"expression":{"type":"string","description":"要计算的表达式,如 '2+3*4'"}}),Tool(name="web_search",description="搜索互联网获取最新信息",func=web_search,parameters={"query":{"type":"string","description":"搜索关键词"}})]

2. 记忆模块:比简单的列表多一点

短期记忆就用一个消息列表保存对话上下文。为了让模型不丢失重要信息,我们可以加入一个历史消息裁剪 + 摘要的简易机制,防止超出 Token 上限。

classMemory:def__init__(self,system_prompt,max_messages=20):self.system_prompt=system_prompt self.messages=[]# 只保留最近的消息self.summary=""# 早期消息的摘要self.max_messages=max_messagesdefadd(self,role,content):self.messages.append({"role":role,"content":content})iflen(self.messages)>self.max_messages:# 将前一部分消息总结(可用LLM完成,这里简化为丢弃前一半)older=self.messages[:self.max_messages//2]self.messages=self.messages[self.max_messages//2:]# 实际项目中应调用 LLM 生成摘要并拼入 system promptself.summary=f"[早期对话摘要] 共省略{len(older)}条消息。"defget_context(self):base=[{"role":"system","content":self.system_prompt+'\n'+self.summary}]returnbase+self.messages

3. Agent 主循环:推理与执行

终于到了最关键的部分。我们将利用 OpenAI 的 Function Calling,让模型决定何时调用工具,何时回复文本。

fromopenaiimportOpenAI client=OpenAI()# 需设置 OPENAI_API_KEY 环境变量classAgent:def__init__(self,tools,system_prompt,model="gpt-4o-mini",max_steps=10):self.tools={t.name:tfortintools}self.system_prompt=system_prompt self.model=model self.max_steps=max_steps self.memory=Memory(system_prompt)defrun(self,user_query):self.memory.add("user",user_query)tool_schemas=[t.to_openai_function()fortinself.tools.values()]forstepinrange(self.max_steps):messages=self.memory.get_context()response=client.chat.completions.create(model=self.model,messages=messages,tools=tool_schemas,tool_choice="auto")msg=response.choices[0].message# 情况1:模型要求调用工具ifmsg.tool_calls:fortool_callinmsg.tool_calls:tool_name=tool_call.function.name tool_args=json.loads(tool_call.function.arguments)print(f"[Agent 动作] 调用工具{tool_name},参数{tool_args}")result=self.tools[tool_name].execute(**tool_args)# 将工具执行结果添加到记忆self.memory.add("tool",result,tool_call_id=tool_call.id)# 将带的 tool_calls 消息也加入记忆(不显示存,但需要在 messages 中体现 assistant 的请求)self.memory.messages.append({"role":"assistant","content":msg.content,"tool_calls":[tc.dict()fortcinmsg.tool_calls]})continue# 进入下一轮循环# 情况2:没有工具调用,视为最终答案final_answer=msg.content self.memory.add("assistant",final_answer)returnfinal_answerreturn"已达到最大执行步数,任务可能未完成。"

注意:上面的代码为了清晰,直接操作了memory.messages添加包含tool_calls的 assistant 消息和对应tool角色消息,这是 OpenAI 对话格式要求。我们在 Memory 类里增加了支持:

# 在 Memory 类中扩展 add 方法,兼容 tool 角色defadd(self,role,content,tool_call_id=None):msg={"role":role,"content":content}iftool_call_id:msg["tool_call_id"]=tool_call_id self.messages.append(msg)# ... 裁剪逻辑

这样我们就拥有了一个完全自主的 Agent。只需几行启动:

system_prompt="你是一个有用的助手,可以调用计算器或搜索工具帮助用户。每次只调用一个工具,收到结果后再决定下一步。"agent=Agent(tools,system_prompt)result=agent.run("现在几点?另外,计算 123 * 456 是多少?")print("最终回复:",result)

四、从玩具到工程化:加入规划与长期记忆

上面这个最小实现已经具备了 Agent 的核心循环,但真实场景下还需要两个重要的能力:

4.1 规划能力(Task Decomposition)

对于复杂问题(比如“帮我调研 AI 在医疗领域的三个主要应用,并生成表格”),模型需要能够先规划再执行。可以通过让 LLM 在第一步输出一份行动计划 JSON来实现,Agent 按照计划逐步执行并在过程中修正。

也可以在系统提示中诱导:

“收到复杂任务时,请先用一句话说明你的执行步骤,然后逐步调用工具,每一步确认结果后再继续。”

更好的做法是增加一个planner工具,允许模型显式地储存和修改任务列表。

4.2 长期记忆与 RAG

当对话过长或需要跨 session 记忆时,短期消息列表不够用。我们可以引入向量数据库(如 Chroma、Pinecone),将重要信息总结后存储为 embedding,再在后续对话中检索相关记忆作为上下文。

步骤:

  1. 对话结束后,将重要事实和决策摘要调用 embedding 模型存入向量库。
  2. 新对话开始时,根据用户问题从向量库检索 Top-K 相关记忆,插入到 System Prompt 中。

这样就构成了真正的长期记忆


五、生产环境必须考虑的硬核问题

从 Demo 到上线,下面几个坑一定不能跳过:

  • 工具安全与沙箱:特别是执行代码/命令的工具,必须严格限制权限,在容器或沙箱环境运行。
  • 成本与延迟控制:设置更短的max_steps,使用便宜的模型(gpt-4o-mini)做规划和简单任务,复杂推理才路由到大模型。
  • 错误恢复与死循环检测:工具执行失败时不要让 Agent 卡死,应把错误信息返回给模型,让它自行修正;超过一定步数则强行终止。
  • 输出验证:对工具参数做严格校验,避免 LLM 的幻觉参数(比如调用web_search传了空字符串)。
  • 可观测性:记录每一步的推理与工具调用日志,便于调试和审计。

六、实战升级:打造一个研究助手 Agent

用一个稍微完整的例子来串联所学:我们要构建一个能搜索并撰写简要研究报告的 Agent。

增加工具

  • web_search(真实 API,如 Tavily)
  • save_note:将重要发现保存到内存笔记,最后供模型总结。

系统提示

“你是专业研究助手。当收到研究主题时:1. 列出需要搜索的 3-4 个子问题;2. 逐个搜索;3. 将有用信息保存笔记;4. 最后整合笔记写 200 字摘要。如果信息不足,请继续搜索。”

实现提示:将笔记存储为 Memory 中的特殊变量,或直接作为一个工具来追加内容。这样 Agent 自动学会了“先搜索,后组织”。

你会发现,这个 Agent 开始展现出类似人类的操作流程——这正是智能体涌现的迷人之处


七、结语:未来属于能驾驭 Agent 思维的人

我们走了一条“0 框架”的路,并不是说 LangChain 和 CrewAI 没有价值,而是只有理解了底层循环、工具交互和记忆管理,你才能真正驾驭这些框架,并在它们不满足需求时,有勇气自己造一个。

从 0 到 1 构建 AI Agent 的旅程到这里告一段落,但它也打开了更大的门:多 Agent 协作、Agent 自进化、代码生成与执行…… 这些都是接下来等待你探索的新大陆。

现在,打开你的代码编辑器,去创造一个专属于你的智能体吧。

http://www.jsqmd.com/news/810605/

相关文章:

  • Cursor Pro破解终极指南:开源工具cursor-free-vip实现AI编程助手永久免费使用
  • 储能项目一操作记录
  • Zed编辑器深色光标主题:提升编码体验的视觉工程实践
  • 5.参考论文的文献引用没有标数字,要不要标数字?
  • 茉莉花插件:如何用Jasminum解决中文文献管理的三大痛点
  • 座机打电话时,能设置在对方屏幕上显示的公司名称吗?开通号码认证业务
  • 工程师如何从错误中学习:构建个人与团队的错误处理系统
  • 基于MCP协议的学术成果商业化AI管道:从论文到商业机会的自动化桥梁
  • 台湾产业转型:从代工制造到创新生态的挑战与机遇
  • 长期使用Taotoken聚合服务对项目API调用成功率的实际影响
  • 从技术段子到工程实践:构建无歧义的硬件开发沟通体系
  • 『订单税率+收货地址校验国家字段』功能上新|跨境运营更高效,Tigshop开源商城系统 JAVA v5.8.23 版本更新
  • 数字时代隐私保护:从法律困境到个人防御与产品设计
  • QML Color 颜色应用示例合集
  • 6.这个论文发表过吗?可以直接用吗?能过查重吗?
  • MySQL数据类型与约束 数值字符串日期
  • 大厂技术人的“隐形天花板”:为什么升到P8就上不去了?
  • 逻辑删除不等于物理销毁:KingbaseES 敏感数据擦除实战
  • 数据删了不等于销毁:KingbaseES敏感数据物理擦除实战指南
  • Taotoken用量看板如何帮助开发者精细化管理API成本
  • 解密猫抓扩展:5个技巧让你成为浏览器资源嗅探高手
  • 7.论文里面的代码、图片等会查重吗?
  • 只知道黑客很酷?普通人学会黑客技术的爽感,远超想象!完整路线指南奉上
  • 旧电脑也能升Win11 22H2?保姆级绕过TPM/CPU检测教程(附卡31%解决方案)
  • TVA重塑智慧城市安防新范式(15)
  • picx-cli:基于GitHub图床的命令行工具,提升开发者图片管理效率
  • 开发AI应用时如何利用Taotoken模型广场进行选型与测试
  • D3KeyHelper终极指南:暗黑3宏工具5分钟快速上手攻略
  • 【Java SE】多线程(二):线程安全、synchronized、volatile与wait/notify详解
  • 5分钟彻底解决Windows激活难题:KMS_VL_ALL_AIO智能激活完全指南