习题

配套代码:code/chapter7

  1. 本章构建了 HelloAgents 框架,并阐述了"为何需要自建Agent框架"。请分析:

    • 在7.1.1节中提到了当前主流框架的四个主要局限性。结合你在第六章习题或实际项目中使用过的某个框架的实际经验,说明这些问题是如何影响开发效率的。
    • HelloAgents 提出了"万物皆为工具"的设计理念,将 Memory、RAG、MCP 等模块都抽象为工具。这种设计有什么优势?是否存在局限性?请举例说明。
    • 对比第四章从零实现的智能体代码和本章的框架化实现,框架化带来了哪些具体的改进?如果让你设计一个框架,你会优先考虑哪些设计原则?
  2. 在7.2节中,我们扩展了 HelloAgentsLLM 以支持多模型供应商和本地模型调用。

    提示:这是一道实践题,建议实际操作

    • 参考7.2.1节的示例,尝试为 HelloAgentsLLM 添加一个新模型供应商的支持(如Gemini、Anthropic、Kim)。要求通过继承方式实现,并能够自动检测该提供商的环境变量。
    • 在7.2.3节中介绍了自动检测机制的三个优先级。请分析:如果同时设置了 OPENAI_API_KEY 和 LLM_BASE_URL="http://localhost:11434/v1",框架最后会选择哪个提供商?这种优先级设计是否合理?
    • 除了本章介绍的 VLLM 和 Ollama,还有 SGLang 等其他本地模型部署方案。请先搜索并了解 SGLang 的基本信息和特点,然后对比 VLLM、SGLang 和 Ollama 这三者在易用性、资源占用、推理速度、推理精度等方面的优劣。
  3. 在7.3节中,我们实现了 Message 类、Config 类和 Agent 基类。请分析:

    • Message 类使用了 Pydantic 的 BaseModel 进行数据验证。这种设计在实际应用中有哪些优势?
    • Agent 基类定义了 run 和 _execute 两个方法,其中 run 是公开接口,_execute 是抽象方法。这种设计模式叫什么?有什么好处?
    • 在 Config 类中,我们使用了单例模式。请解释什么是单例模式,为什么配置管理需要使用单例模式?如果不使用单例会导致什么问题?
  4. 在7.4节中,我们动手进行了四种 Agent 范式的框架化实现。

    提示:这是一道实践题,建议实际操作

    • 对比第四章从零实现的 ReActAgent 和本章框架化的 ReActAgent,列举3个具体的改进点,并说明这些改进如何提升了代码的可维护性和可扩展性。
    • ReflectionAgent 实现了"执行-反思-优化"循环。请扩展这个实现,添加一个"质量评分"机制:在每次反思后,让 LLM 对当前版本的输出打分,只有分数低于阈值时才继续优化,否则提前终止。
    • 请设计并实现一个新的 Agent 范式 Tree-of-Thought Agent,要求继承 Agent 基类,它能够在每一步生成多个可能的思考路径,然后选择最优路径继续。
  5. 在7.5节中,我们构建了工具系统。请思考以下问题:

    • BaseTool 类定义了 execute 抽象方法,所有工具都必须实现这个方法。请解释为什么要强制所有工具实现统一的接口?如果某个工具需要返回多个值(如搜索工具返回标题、摘要、链接),应该如何设计?
    • 在7.5.3节中实现了工具链(ToolChain)。请设计一个实际的应用场景,需要串联至少3个工具,并画出工具链的执行流程图。
    • 异步工具执行器(AsyncToolExecutor)使用了线程池来并行执行工具。请分析:在什么情况下并行执行工具能带来性能提升?
  6. 框架的可扩展性是设计的重要考量因素之一。你现在要扩展 HelloAgents 框架,为其实现一些有趣的新功能和特性。

    • 首先为 HelloAgents 添加一个"流式输出"功能,使得 Agent 在生成响应时能够实时返回中间结果(类似 ChatGPT 用户界面的打字效果)。请设计这个功能的实现方案,说明需要修改哪些类和方法。
    • 然后为框架添加"多轮对话管理"功能,能够自动管理对话历史、支持对话分支和回溯,你会如何设计?需要新增哪些类?如何与现有的 Message 系统集成?
    • 最后请为 HelloAgents 设计一个"插件系统",允许第三方开发者通过插件的方式扩展框架功能(如添加新的 Agent 类型、新的工具类型等),而无需修改框架核心代码。要求画出插件系统的架构图并说明关键接口。