吴恩达新课程:Agentic AI(笔记5)
Module 3: 工具使用(Tool use)
3.1 什么是工具?
核心思想:工具即函数,模型自主决策 关键在于,模型拥有自主决策权。它不再是被动地根据内部知识库生成答案,而是能主动判断:在当前情境下,是否需要、以及应该调用哪个工具来完成任务。
类比:就像人类借助锤子、扳手等工具能完成徒手无法做到的事情一样,语言模型通过调用“函数工具”,也能突破自身训练数据和能力的限制,变得无比强大。
例子:以“现在几点?”为例,清晰展示了工具使用的完整闭环:
输入提示 (Input Prompt): 用户提问 “What time is it?”。
模型决策 (Model Decision): LLM 意识到自己无法提供实时时间,于是决定调用名为 get_current_time() 的工具。
工具执行 (Tool Execution): 系统执行该函数,返回精确的时间值,例如 15:20:45。
结果反馈 (Result Feedback): 这个时间值被作为新的上下文(对话历史)回传给 LLM。
最终输出 (Final Output): LLM 结合这个新信息,生成自然语言回复:“It's 3:20pm.”
整个过程的关键点:
工具是函数:get_current_time() 是一段 Python 代码,它负责与系统时钟交互并返回字符串。
模型自主选择:模型自行决定何时、何地调用哪个工具。
动态上下文:工具返回的结果会融入对话历史,供模型后续推理使用。

何时调用,何时不调用?
工具使用的一个重要特性是条件性调用。
模型并非对所有问题都盲目调用工具,而是能智能判断。
调用工具的例子:当被问及“现在几点?”,模型知道需要实时数据,因此调用 get_current_time()。
不调用工具的例子:当被问及“绿茶含多少咖啡因?”,模型可以基于其内部知识库直接回答:“Green tea typically contains 25-50 mg of caffeine per cup.”,无需调用任何工具。
这体现了模型的“智能”——它能区分哪些信息是静态的(可内化),哪些是动态的(需外求)。

多工具协作
对于更复杂的请求,模型可以串联调用多个工具,形成工作流。
案例:日历助理
用户请求: “请在周四我的日历中找一个空闲时段,并与Alice预约。”
- 提供的工具集:
check_calendar(): 查询日历,返回空闲时段。
make_appointment(): 创建预约。
delete_appointment(): 取消预约。
- 模型执行流程:
首先调用 check_calendar(),获得结果:“Thursday, 3pm; Thursday, 4pm; Thursday, 6pm”。
基于返回的信息,模型决定选择“3pm”这个时段。
接着调用 make_appointment(time="3pm", with="Alice")。
工具返回确认信息:“Meeting created successfully!”。
最终,模型整合信息,回复用户:“Your appointment is set up with Alice at 3 PM Thursday.”

总结
工具使用是构建下一代 AI 应用的关键技术。它让语言模型从“只会聊天”的伙伴,进化为能够“动手做事”的智能助手。
核心价值:
超越知识边界:通过调用工具,模型可以获取实时数据、访问数据库、执行计算。
实现复杂逻辑:支持多步推理和工具链协作,处理现实世界的复杂需求。
提升应用价值:无论是餐厅推荐、零售分析还是个人日程管理,都能因工具而变得更实用、更强大。
3.2 创建一个工具
LLM本身并不会直接执行代码或调用函数,它被训练的核心能力是生成文本。
如何让LLM学会调用函数的过程,核心思想是模型不直接调用,而是“请求”调用。工具其实就是一些代码/函数。如今的主流语言模型都经过直接训练去使用工具,没有训练就必须得写提示词来告诉模型如何使用工具。
实现工具使用:
开发者编写工具函数:例如 get_current_time()。
开发者编写系统提示词 (System Prompt):告诉模型,如果它想使用某个工具,应该如何格式化它的输出。
模型根据提示词输出特定格式的文本:这个文本不是最终答案,而是一个“请求”,例如 FUNCTION: get_current_time()。
开发者编写解析代码:读取模型的输出,识别出这个“请求”,然后真正地调用对应的函数。
将函数结果回传给模型:把函数返回的结果作为新的上下文输入给模型,让它生成最终的自然语言回复。
类比:就像你不能直接命令一个只会说话的人去帮你买咖啡,但你可以告诉他:“如果你想去买咖啡,请说‘我要买一杯美式’。” 然后你听到这句话后,自己去帮他买。
案例一:以获取此刻时间为例
编写工具函数
from datetime import datetimedef get_current_time():"""Returns the current time as a string"""return datetime.now().strftime("%H:%M:%S")
设计系统提示词 (System Prompt)
“你有一个名为 get_current_time 的工具。要使用它,请严格按照以下格式输出:FUNCTION: get_current_time()。”
模型响应与开发者解析 当用户提问 “What time is it?” 时:
LLM 会根据提示词,输出:FUNCTION: get_current_time()
开发者的代码会检测到输出中包含 “FUNCTION” 关键字。
代码会从输出中提取出 get_current_time() 这个函数名和参数。
代码随后实际调用 get_current_time() 函数,得到结果,比如 "08:00:00"。
将结果反馈给模型
开发者将结果 "08:00:00" 和之前的对话历史一起,再次输入给模型。
模型生成最终回复
模型现在知道了“当前时间是 08:00:00”,于是可以生成自然语言回答:“It's 8am.”

案例二:获取指定时区的时间
第一步:编写带参数的工具函数
from datetime import datetime
from zoneinfo import ZoneInfodef get_current_time(timezone):"""Returns current time for the given time zone"""timezone = ZoneInfo(timezone)return datetime.now(timezone).strftime("%H:%M:%S")
第二步:更新系统提示词
“你有一个名为 get_current_time 的工具,它可以接受一个时区参数。要使用它,请严格按照以下格式输出:FUNCTION: get_current_time("timezone")。”
第三步:模型响应与开发者解析
当用户提问 “What time is it in New Zealand?” 时:
LLM 会输出:FUNCTION: get_current_time("Pacific/Auckland")
开发者的代码解析出函数名 get_current_time 和参数 "Pacific/Auckland"。
代码调用函数,得到结果,比如 "04:00:00"。
结果被回传给模型。
第四步:模型生成最终回复
模型结合新信息,生成最终回答:“It's 4am in New Zealand.”

总结:四步循环
提供工具 (Provide the Tool):开发者编写好功能函数。
告知模型 (Tell the LLM):通过系统提示词,明确告诉模型有哪些工具可用,以及如何“请求”调用它们(即输出什么格式的文本)。
解析并执行 (Parse and Execute):开发者编写代码,监听模型的输出,识别其“请求”,并实际执行对应的函数。
反馈结果 (Feed Back Result):将函数执行的结果作为新的上下文,送回给模型,让它继续推理或生成最终答案。
这个流程的关键在于,开发者扮演了“翻译官”和“执行者”的角色,弥合了语言模型的“文本生成”能力与现实世界“函数执行”能力之间的鸿沟。
