论文单位:上海交通大学 2 上海人工智能研究院 3 全球人工智能与机器人峰会 项目地址:https://github.com/GAIR-NLP/DeepResearcher 发表时间:2025年4月
这篇论文研究的是如何训练大型语言模型(LLM)成为一个真正强大的“深度研究”智能体(Agent)。它专注于让AI不仅能回答问题,更能像一个人类研究员一样,通过在真实的互联网上进行搜索、阅读、分析和整合信息,来解决复杂、开放性的问题。
论文所处的领域是人工智能,具体来说是大型语言模型(LLM)驱动的智能体(Agent)技术。
想象一下,我们希望AI助手不仅仅是聊天机器人,而是能帮我们完成复杂任务的“数字员工”。其中一个非常重要的任务就是信息研究——比如,为一篇报告收集所有相关资料,或者调查一个商业竞争对手的最新动态。目前,让AI连接互联网进行搜索已经是常规操作了,但这篇论文的目标更高:它不满足于简单的“搜索-粘贴”,而是追求一种能进行多步骤、迭代式调查的“深度研究”能力。
论文明确指出了当前AI研究代理存在的两大核心问题:
因此,论文要解决的核心问题是:如何在一个真实的、开放的、充满噪音的互联网环境中,通过端到端的强化学习,训练出一个既强大又稳健的深度研究AI智能体?
解决这个问题非常重要,其价值和影响深远:
作者的切入点非常明确和具有批判性:他们认为**“训练环境”本身不是一个可以妥协的实现细节,而是一个决定成败的根本性因素**。
与之前的工作相比,他们的独特之处在于:
这项研究的动机与当前几个重要的技术和社会趋势紧密相连:
好的,请看以下对该论文相关工作部分的专业分析。
在探讨本文的创新点之前,我们需要了解该领域的研究现状。通过梳理《DeepResearcher》论文中“Related Work”章节的内容,我们可以清晰地看到作者是如何将自己的工作置于现有研究图谱之中,并针对性地解决前人研究的不足。
根据论文的综述,当前利用大语言模型(LLM)进行深度研究(或信息检索)的工作主要分为两大方向:基于提示的方法(Prompt-Based)和基于训练的方法(Training-Based)。后者又可细分为监督微调(SFT)和强化学习(RL)。这些方法在不同的交互环境中运行,即本地RAG环境或真实网络搜索环境。
具体总结如下表所示:
研究方向 | 子方向 | 核心思想 | 论文中提及的代表性工作 |
---|---|---|---|
基于提示的搜索代理 (Prompt-Based) | - | 依赖人工设计的提示词(Prompts)和预设工作流来指导LLM与外部知识源进行交互。 | OpenResearcher, AirRAG, IterDRAG, Plan*RAG, Search-o1, Open Deep Search |
基于训练的搜索代理 (Training-Based) | 监督微调 (SFT) | 在高质量的“搜索-推理-回答”轨迹数据上对模型进行微调,以模仿专家行为。 | CoRAG (使用MCTS生成数据) |
强化学习 (RL) | 通过与环境交互和奖励信号,让模型自主学习最优的搜索和推理策略,无需人工指定行为。 | Search-R1, ReSearch, R1-Searcher, OpenAI Deep Research (方法未公开) | |
交互环境 (Training Environments) | 本地RAG环境 | 在一个固定的、预先构建好的本地知识库(如维基百科语料库)中进行信息检索。 | 主流RAG框架, Search-R1, ReSearch |
真实网络搜索环境 | 直接与实时搜索引擎(如Google, Bing)交互,访问和处理开放互联网上的动态信息。 | Search-o1 (部分设置), R1-Searcher (部分设置), 以及本文的DeepResearcher |
当前领域的主流技术路线可以根据其实现复杂性和对人工依赖程度进行划分,从完全依赖人工设计到完全自主学习。
技术路线 | 核心技术 | 交互环境 | 优点 | 局限性(如论文所述) |
---|---|---|---|---|
提示工程 (Prompt Engineering) | 手动设计复杂的提示词和固定的多步工作流(如ReAct框架)。 | 本地RAG或真实网络 | 实现简单,无需训练。 | 行为模式僵化,适应性差,性能脆弱,依赖大量人工调试。 |
监督微调 (SFT) | 在专家数据上进行微调,学习特定的搜索和推理模式。 | 主要为本地RAG | 比提示工程更稳定,能学习复杂行为。 | 依赖高质量的监督信号,泛化能力弱,可能存在计算开销大的问题(如MCTS)。 |
基于RAG的强化学习 (RAG-based RL) | 使用RL算法(如PPO, GRPO)在本地知识库中训练代理。 | 本地RAG | 能够自主探索策略,超越SFT的固定模式。 | 训练环境过于理想化和受控,无法处理真实网络的复杂性。 |
基于真实网络的强化学习 (Web-based RL) | 使用RL算法在与真实搜索引擎交互的环境中进行端到端训练。 | 真实网络 | **(此为DeepResearcher采用的路线)**能学习处理真实世界噪声、延迟和多样化信息源的鲁棒策略。 | 实现复杂,面临API速率限制、反爬虫、网络延迟等工程挑战。 |
论文作者着重强调了现有方法的几大核心局限,这些也是驱动其研究的动机:
DeepResearcher明确地将自己定位为首个在真实网络环境中规模化端到端训练深度研究代理的综合性强化学习框架。
它的定位可以从两个维度理解:
因此,DeepResearcher的工作可以看作是将RL agent训练从一个受控的模拟环境(Controlled Simulation)推进到了一个开放的真实环境(Real-world Environment),填补了现有开源研究中的一个重大空白。
DeepResearcher并非凭空创造,而是在前人工作的基础上进行了关键的借鉴和实质性的改进:
GRPO (Group Relative Policy Optimization)
算法,这是从DeepSeek-R1
等工作中验证过的有效算法。综上所述,DeepResearcher的研究建立在现有RL for LLM的浪潮之上,但通过将训练环境推向更具挑战性的真实世界,它不仅显著提升了模型在研究任务上的性能和泛化能力,也揭示了在这种真实环境中训练所能涌现出的更高级认知行为(如规划、交叉验证、反思等)。
好的,我们来深入解读这篇论文。
基于前文对研究背景和现状的分析,本论文的创新主要体现在以下几个层面,它不仅提出了一个新颖的框架,更重要的是,它挑战了现有研究范式中的一个核心假设,并用实践证明了一条更艰难但更有效的路径。
本论文的核心创新,可以概括为以下三点:
这些创新的灵感主要源于对现有方法根本性局限的深刻洞察,并借鉴了其他领域的成功经验:
本研究是典型的跨界融合产物:
总而言之,DeepResearcher的真正“闪光点”在于它拒绝走捷径,直面真实世界研究任务最核心的挑战——处理开放、动态和混乱的信息。通过在真实环境中磨砺模型,它不仅在性能上取得了突破,更让我们看到了通往更强大、更可靠、甚至更“有智慧”的AI研究助手的曙光。
好的,我将以专业的论文分析助手身份,为您详细解读这篇《DeepResearcher》论文提出的解决方案和方法细节。
为了解决现有研究代理(Agent)要么依赖脆弱的提示工程、要么在脱离现实的RAG(检索增强生成)环境中训练而无法适应真实网络复杂性的问题,论文提出了 DeepResearcher,一个通过在真实世界环境中进行大规模强化学习(RL)来端到端训练LLM研究代理的综合框架。
该框架的核心思想是:让智能体直面并学习驾驭开放、嘈杂、动态的真实互联网,而不是在被“净化”和“预设”的静态知识库中进行模拟训练。通过这种方式,智能体能够自行发现并优化解决复杂研究问题的策略,从而获得更强的鲁棒性和泛化能力。
DeepResearcher的整体框架是一个基于强化学习的闭环系统,它使LLM代理能够通过与真实网络环境的反复交互来学习如何进行深度研究。其工作流程可以概括为“思考-行动-观察-学习”的迭代循环。
如下图所示,整个过程从一个用户问题开始,代理通过一系列的推理(think
)和工具调用(web_search
, web_browse
)来收集、整合信息,直到它认为信息足够充分,最终生成答案(answer
)。
图3: DeepResearcher的工作流程示意图。左上角展示了系统并行处理一批问题,每个问题都进行多次独立的探索(rollout)。右侧和底部则详细描绘了单个问题的解决轨迹,包括思考、搜索、浏览、信息提取和最终回答的迭代过程。
这个框架的方法论核心是:将复杂的“深度研究”任务分解为一系列可由模型学习和执行的基本步骤,并通过结果驱动的奖励信号(outcome-based reward)来优化模型选择这些步骤的策略。
DeepResearcher方法由以下几个关键部分构成:
a. 深度研究轨迹(Deep Research Trajectory) 这是代理解决问题的单次完整路径,由一系列的“思考-行动”对组成。
<think>
): 在每次行动前,模型被强制生成一段“思考”文本,放在<think>
标签内。这使得模型的决策过程更加透明,并鼓励其进行显式的规划和推理。<answer>
): 当模型判断已收集到足够信息时,它会生成最终答案,并用<answer>
标签包裹。b. 应对真实网络环境挑战的工程解决方案 在真实网络环境中进行大规模RL训练会遇到许多在RAG环境中不存在的工程难题。
c. 强化学习训练框架
d. 奖励机制 (Reward Mechanism) 奖励是指导模型学习方向的指挥棒。DeepResearcher使用了简单但有效的结果导向型奖励:
我们可以通过一个完整的例子来理解这些部分的协同工作:
think
): “我需要先找出2019年戛纳电影节金棕榈奖的电影,然后再找这部电影的导演,最后找导演毕业的大学。”act
): 生成 web_search(query="2019 Cannes Film Festival Palme d'Or winner")
。observe
): 看到搜索结果,知道获奖电影是《寄生虫》。think
): “好的,现在我知道电影是《寄生虫》。下一步是找到它的导演。”act
): 生成 web_search(query="director of Parasite movie")
。observe
): 知道导演是奉俊昊。think
): “现在需要查一下奉俊昊的教育背景。我应该访问他的维基百科页面。”act
): 生成 web_browse(url="https://en.wikipedia.org/wiki/Bong_Joon-ho")
。observe
): 接收到从网页中提取出的关键信息“Korean Academy of Film Arts”。think
): “我已经找到了所有信息:获奖电影是《寄生虫》,导演是奉俊昊,他毕业于韩国电影艺术学院。我可以回答问题了。”act
): 生成 <answer>Bong Joon-ho, the director of Parasite, graduated from the Korean Academy of Film Arts.</answer>
。think
、tool_call
或answer
。综上所述,DeepResearcher的解决方案是一个设计精巧、工程上可行的系统。它通过将强化学习从受控环境解放到真实世界,并辅以创新的浏览代理和可扩展的工程架构,成功地训练出一个能够自主学习并展现出复杂研究能力的LLM智能体,为构建更强大、更通用的AI研究助手开辟了新的道路。
好的,请看以下对该论文实验设计与验证方法的专业分析。
为验证所提方法(DeepResearcher)的有效性,论文设计了一系列全面的实验,旨在证明通过在真实网络环境中进行强化学习(RL)训练的智能体,在深度研究任务上优于基于提示工程和基于受控RAG环境的RL方法。
论文的实验设置围绕着数据集选择、基准模型对比和多维度评估指标三个核心展开,以全面衡量模型在不同场景下的性能。
实验要素 | 具体设置 | 目的/说明 |
---|---|---|
基础模型 | Qwen2.5-7B-Instruct | 选用一个有竞争力的开源模型作为训练和对比的骨干。 |
训练数据集 | 来源:NQ, TQ, HotpotQA, 2WikiMultiHopQA。特点:混合了单跳(NQ, TQ)和多跳(HotpotQA, 2Wiki)问题。处理:通过两阶段过滤(低质量问题过滤、数据污染检测)构建了80,000个样本的训练集,并特意使多跳问题占75%。 | 1. 模拟研究复杂性:多跳问题更能反映深度研究中信息综合的需求。2. 保证实验有效性:数据污染检测确保模型必须学习使用搜索工具,而非依赖其参数化记忆,这是验证真实研究能力的关键前提。 |
评估数据集 | 域内 (In-Domain):NQ, TQ, HotpotQA, 2Wiki的开发集。域外 (Out-of-Domain, OOD):MuSiQue, Bamboogle, PopQA。 | 1. 域内评估:验证模型在训练数据分布内的性能。2. 域外评估:测试模型的泛化能力,特别是Bamboogle数据集,其答案不限于维基百科,直接挑战了仅依赖特定知识库的RAG方法。 |
基准测试 (Baselines) | 1. 基于提示工程的方法: - CoT Only (无搜索) - CoT + RAG (本地RAG搜索) - Search-o1* (本地RAG多步搜索) - Search-o1 + Web Search (真实网络多步搜索)2. 基于训练的方法: - Search-r1-base / instruct (本地RAG环境RL训练) - R1-Searcher (本地RAG训练,推理时用Web搜索) | 1. 逐级对比:从无搜索到有搜索,从本地RAG到真实网络,清晰地展示了不同环境和方法带来的影响。2. 核心对比:将DeepResearcher与同样使用RL的Search-r1和R1-Searcher对比,旨在隔离并凸显在真实网络环境中训练的核心优势。 |
评估指标 (Metrics) | 1. 基于规则的指标:F1分数。2. 基于模型的评估 (MBE):使用GPT-4o-mini作为裁判,判断答案正确性(准确率)。 | 1. 定量衡量:F1分数与训练的奖励函数对齐,直接反映模型优化目标。2. 质量评估:MBE能够更好地评估答案的语义正确性,弥补了F1分数在处理长文本或不同表述时的不足,被认为是更可靠的指标。 |
实验设计的核心思路是控制变量和逐步递进,以隔离并验证其核心贡献:在真实网络环境中进行端到端RL训练的必要性。
其合理性体现在以下几点:
论文的对比实验设计精巧,形成了一个清晰的比较矩阵,尽管没有明确的“消融研究”章节,但其基准选择实际上起到了消融分析的作用。
对比方法:
消融实验设计: 论文的基准比较逻辑实质上构成了对环境和方法的消融分析:
CoT Only
(无工具)是性能基线。Search-o1*
(本地RAG)和Search-o1 + Web Search
(真实网络)展示了不同环境对同一提示工程方法的影响。Search-r1
/R1-Searcher
(RAG环境训练)和DeepResearcher
(真实网络环境训练)直接验证了论文的核心假设。此外,第6.1节的训练动态分析(图4)也提供了一种时间维度上的分析,展示了随着RL训练的进行,模型的性能(F1)、推理步数和响应长度都在增加,表明了RL训练过程的有效性。
实验设计充分且有力地验证了所提方法的有效性。
潜在的局限是,实验虽模拟了“研究”,但仍基于有标准答案的QA任务。真正的“深度研究”可能涉及更开放、无确定答案的探索过程,这在当前实验中未完全覆盖,但论文已在结论中提及此为未来方向。
通过上述实验设计,论文得到了以下关键结果,这些结果共同验证了在真实网络环境中进行强化学习训练的有效性。
1. 主要实验结果与量化指标
论文在7个开放域问答数据集上进行了评估,包括4个域内(In-Domain)和3个域外(Out-of-Domain)数据集。关键性能指标为模型评估(MBE)准确率,DeepResearcher的表现如下:
方法 | 环境 | In-Domain (HotpotQA, MBE) | Out-of-Domain (Bamboogle, MBE) |
---|---|---|---|
Search-o1 + Web (提示工程) | Web Search | 42.4% | 53.6% |
Search-r1-base (RAG+RL) | Local RAG | 63.0% | 57.6% |
R1-Searcher (RAG+RL) | Web Search | 53.1% | 65.6% |
DeepResearcher (本文方法) | Web Search | 64.3% | 72.8% |
2. 结果对比与方法优势
对比结果凸显了DeepResearcher的显著优势。首先,相较于同样使用真实网络搜索的提示工程方法(Search-o1 + Web),DeepResearcher在Bamboogle数据集上提升了19.2个百分点,证明了强化学习训练远优于固定的提示模板。其次,相较于在受控RAG环境中训练的RL方法(Search-r1-base),DeepResearcher在需要非维基百科知识的Bamboogle数据集上取得了15.2个百分点的巨大优势。这表明,在真实、嘈杂的网络环境中训练,能让模型学会处理多样化和非结构化信息,而这是RAG环境无法模拟的。即使是让RAG训练的模型(R1-Searcher)在推理时访问网络,其性能也远不及DeepResearcher,这强调了训练环境而非仅仅推理环境的重要性。
3. 结果对论点的支持
这些量化结果有力地支持了论文的核心论点:在真实世界环境中进行端到端强化学习训练,是构建强大研究智能体的根本要求,而非简单的实现细节。在域外数据集上的卓越表现(如Bamboogle上的72.8%)证明,DeepResearcher学到了通用的信息检索与综合能力,而非仅仅过拟合训练数据。此外,定性分析中观察到的规划、交叉验证、反思和诚实等“涌现行为”,进一步解释了其高性能背后的原因——模型自主发展出了更接近人类研究员的复杂认知策略。
4. 关键结论
作者从结果中得出以下结论:
5. 结论的可靠性与普适性
该结论具有较高的可靠性。研究者通过严格的数据清洗和去污染操作,确保了模型是在学习“如何搜索”而非“回忆答案”。全面的基线对比和在多个域外数据集上的验证,增强了结论的说服力。
然而,其普适性存在一定边界。当前实验主要集中在有明确、简短答案的问答任务上。对于需要生成长篇报告或进行高度主观分析的“深度研究”任务,目前基于F1分数的奖励机制可能不足。尽管如此,该研究为更复杂的任务指明了一条极具前景的技术路径,其核心思想——在真实环境中学习——具有广泛的适用价值。
尽管取得了上述成果,本研究仍有进一步探索和改进的空间。DeepResearcher通过在真实网络环境中进行强化学习,在构建自主研究代理方面取得了显著进展,但其方法论、应用范围和未来潜力仍为后续研究留下了广阔的天地。
论文在正文中明确指出了几个可以立即着手的后续研究方向:
top-k
)。一个明确的改进方向是让LLM代理本身动态地决定需要检索多少搜索结果。例如,对于简单问题可能只需要top-3
,而对于复杂或有争议的话题,代理可能会决定需要top-20
来获取更多样化的视角。除了论文自身提到的方向,其技术框架也存在一些内在局限性,为改进提供了空间:
<article>
, <h1>
, <table>
标签)或进行语义分析,直接定位到网页中最相关的部分,从而大幅提升信息获取的速度和准确性。DeepResearcher框架的核心思想——在真实、动态环境中通过RL学习复杂任务——具有很强的通用性,可以扩展到多个领域:
结合当前大模型和AI Agent的发展趋势,以下几个方向可能最具研究价值:
基于对论文和领域的思考,以下是几个论文未明确提及但同样具有深远价值的研究方向:
search
和browse
工具。一个更高级的代理不仅应该会使用工具,还应该能够主动学习新工具的使用方法(例如,通过阅读API文档),甚至在现有工具无法满足需求时,通过编写代码创造新工具(例如,编写一个专门用于从特定网站抓取数据的Python脚本)。这标志着代理从工具使用者向工具创造者的进化。好的,我们已经深入解读了这篇关于DeepResearcher的论文。该研究的核心在于构建了一个通过强化学习(RL)在真实网络环境中进行端到端训练的LLM智能体,使其能够处理复杂的深度研究任务。
其方法论的关键创新点包括:
这些要素共同构成了一个能够学习如何在开放、无限制的互联网上进行有效研究的强大智能体。
最后,我们将论文的核心算法用Python风格的伪代码表示如下,以帮助理解其实现思路。
以下伪代码概述了DeepResearcher的训练框架,重点展示了其基于强化学习(GRPO)的训练循环,以及与真实网络环境(通过搜索和浏览工具)的交互过程。
import torch
import numpy as np
from typing import List, Dict
# --- 前置设定与超参数 ---
# 假设我们有一个预训练好的指令微调模型作为基础
BASE_MODEL = "Qwen2.5-7B-Instruct"
# 强化学习相关超参数
NUM_ROLLOUTS_PER_PROMPT = 16 # 每个问题生成的轨迹数量 G
MAX_TOOL_CALLS = 10 # 每条轨迹最大工具调用次数
KL_BETA = 0.1 # KL散度惩罚系数
CLIP_EPSILON = 0.2 # PPO/GRPO中的裁剪系数
BATCH_SIZE = 256 # 每步训练使用的问题数量
class DeepResearcherTrainer:
"""
DeepResearcher的训练器,负责实现基于GRPO的强化学习流程。
"""
def __init__(self):
# 初始化策略模型、参考模型和用于采样的旧策略模型
self.policy_model = self.load_model(BASE_MODEL)
self.reference_model = self.load_model(BASE_MODEL) # 用于计算KL散度的参考模型,通常固定
self.old_policy_model = self.load_model(BASE_MODEL) # 用于生成轨迹的模型,定期更新
# 初始化与真实世界环境交互的工具
self.search_tool = WebSearchTool()
self.browsing_agent = WebBrowsingAgent()
def load_model(self, model_name):
# 实际加载模型的辅助函数 (例如,从Hugging Face Hub)
# return AutoModelForCausalLM.from_pretrained(model_name)
pass # 伪代码中省略具体实现
def run_rollout(self, model, prompt: str) -> Dict:
"""
为单个问题生成一条完整的交互轨迹 (trajectory)。
轨迹包含模型的思考、工具调用、环境观察和最终答案。
"""
history = f"User Question: {prompt}\n"
trajectory_tokens = []
for _ in range(MAX_TOOL_CALLS):
# 1. 模型生成下一步的思考和行动
# model.generate() 会生成包含 <think>...</think> 和工具调用JSON的文本
action_text = model.generate(history, stop_tokens=["<answer>"])
trajectory_tokens.append(action_text) # 记录模型生成的部分
history += action_text
# 2. 解析行动并与环境交互
if "<web_search>" in action_text:
query = self.parse_tool_call(action_text, "web_search")
# 调用真实的搜索引擎API
observation = self.search_tool.execute(query)
elif "<web_browse>" in action_text:
url = self.parse_tool_call(action_text, "web_browse")
# 调用专门的浏览智能体处理网页
observation = self.browsing_agent.execute(url, history)
else:
break # 如果没有工具调用,则可能直接生成答案
# 3. 将观察结果加入历史,作为下一次生成的上下文
history += f"\n<observation>{observation}</observation>\n"
# 4. 生成最终答案
final_answer_text = model.generate(history, stop_tokens=["</answer>"])
trajectory_tokens.append(final_answer_text)
return {
"full_trajectory": "".join(trajectory_tokens),
"final_answer": self.parse_final_answer(final_answer_text)
}
def calculate_reward(self, trajectory: Dict, ground_truth: str) -> float:
"""
根据轨迹的最终答案和标准答案计算奖励。
"""
# 格式惩罚
if trajectory["final_answer"] is None or "format_error": # 假设有格式错误标志
return -1.0
# 使用F1分数作为核心奖励
predicted_answer = trajectory["final_answer"]
f1_score = self.compute_f1(predicted_answer, ground_truth)
return f1_score
def compute_grpo_loss(self, rollouts: List[Dict], rewards: List[float]):
"""
计算GRPO损失函数。
"""
advantages = torch.tensor(rewards) - torch.mean(torch.tensor(rewards))
# 从rollouts中提取模型生成的token序列
sequences = [r['full_trajectory'] for r in rollouts]
# 计算新旧策略下生成序列的对数概率
# **关键**: 计算loss时,需要mask掉<observation>部分,因为这部分是环境的反馈,不应参与梯度计算
log_probs_policy = self.policy_model.get_log_probs(sequences, mask_observations=True)
log_probs_old_policy = self.old_policy_model.get_log_probs(sequences, mask_observations=True)
# 计算策略比率
ratio = torch.exp(log_probs_policy - log_probs_old_policy)
# 计算裁剪后的目标函数
clipped_advantage = torch.clamp(ratio, 1 - CLIP_EPSILON, 1 + CLIP_EPSILON) * advantages
policy_objective = torch.min(ratio * advantages, clipped_advantage)
# 计算KL散度惩罚
kl_div = self.policy_model.kl_divergence(self.reference_model, sequences)
# 最终损失 (取负号因为我们要最大化目标)
loss = -(policy_objective.mean() - KL_BETA * kl_div.mean())
return loss
def train(self, dataset: List[Dict]):
"""
主训练循环。
"""
optimizer = torch.optim.Adam(self.policy_model.parameters())
for batch in self.get_data_loader(dataset, BATCH_SIZE):
all_rollouts = []
all_rewards = []
# --- 1. Rollout阶段: 使用旧策略并行生成大量轨迹 ---
for item in batch:
prompt = item['question']
ground_truth = item['answer']
for _ in range(NUM_ROLLOUTS_PER_PROMPT):
# 使用旧策略(固定)来生成轨迹
rollout = self.run_rollout(self.old_policy_model, prompt)
reward = self.calculate_reward(rollout, ground_truth)
all_rollouts.append(rollout)
all_rewards.append(reward)
# --- 2. 优化阶段: 使用收集到的轨迹和奖励来更新策略模型 ---
loss = self.compute_grpo_loss(all_rollouts, all_rewards)
optimizer.zero_grad()
loss.backward()
optimizer.step()
# --- 3. 更新旧策略模型 ---
# 定期将优化后的策略模型权重同步到旧策略模型
# if step % SYNC_INTERVAL == 0:
# self.old_policy_model.load_state_dict(self.policy_model.state_dict())
class WebSearchTool:
"""模拟与真实搜索引擎API交互的工具。"""
def execute(self, query: str) -> str:
# 实际实现会调用Google/Bing/Serper等API
# 同时处理API速率限制、缓存和重试机制
print(f"Executing search for: '{query}'")
# 返回格式化的搜索结果片段
return " [{'title': '...', 'url': '...', 'snippet': '...'}, ...]"
class WebBrowsingAgent:
"""
一个专门的智能体,负责浏览网页并提取信息。
这是论文中提到的Multi-Agent方法的核心。
"""
def __init__(self):
# 浏览智能体本身也可以是一个小型的LLM
self.reading_llm = self.load_model("small_extraction_model")
def execute(self, url: str, query_context: str) -> str:
"""模拟人类阅读行为,分段处理并提取信息。"""
print(f"Browsing URL: {url}")
try:
full_page_content = self.crawl_webpage(url)
page_segments = self.segment_page(full_page_content)
extracted_info = []
for i, segment in enumerate(page_segments):
# 智能体判断当前段落是否与问题相关
relevance_prompt = f"Context: {query_context}\n\nWebpage Segment: {segment}\n\nIs this segment relevant to the user's question? Extract key information if so."
# 假设此LLM能提取相关信息或返回空
info = self.reading_llm.extract(relevance_prompt)
if info:
extracted_info.append(info)
# 模拟“如果开头部分不相关则跳过”的策略
if i > 2 and not extracted_info:
break # 如果前几段都无关,则停止浏览,节省资源
return " ".join(extracted_info) if extracted_info else "No relevant information found on this page."
except Exception as e:
return f"Failed to browse page: {e}"
def crawl_webpage(self, url):
# 伪代码:实际会使用requests/BeautifulSoup等处理反爬和解析
pass
def segment_page(self, content):
# 伪代码:将HTML内容分割成有意义的文本块
pass
DeepResearcherTrainer
是整个训练流程的控制器。它初始化了三个模型:policy_model
(正在优化的模型)、reference_model
(用于KL散度计算的稳定基线)和old_policy_model
(用于数据采集的策略,定期更新以减少策略漂移)。run_rollout
函数是算法的核心交互循环。它模拟了智能体的一次完整解题过程:从接收问题开始,通过多次“思考-行动-观察”的循环来收集信息,直到最终给出答案。这个函数真实地反映了智能体如何与WebSearchTool
和WebBrowsingAgent
进行交互。WebBrowsingAgent
是该方法的一个关键创新。它不是简单地返回整个网页内容,而是通过一个内部的reading_llm
模拟人类阅读和筛选信息的过程。这种分段、增量式的提取方式能有效应对冗长且充满噪声的网页,是其优于传统RAG方法的关键之一。calculate_reward
函数体现了“结果导向”的RL思想。奖励仅在轨迹结束时根据最终答案的质量(F1分数)计算,而不是对中间步骤进行奖励,这使得智能体可以自由探索不同的解题路径。compute_grpo_loss
函数将GRPO算法的核心思想转化为代码逻辑。它利用收集到的轨迹计算优势(advantage),并通过策略比率和裁剪来稳定更新,同时用KL散度惩罚来防止策略模型偏离原始的语言能力太远。关键点是损失计算时会屏蔽掉环境反馈(observation),确保模型只学习它自己应该生成的内容。train
函数将所有部分串联起来,执行经典的“采集-优化”循环。它首先用固定的旧策略old_policy_model
生成一批数据,然后用这批数据对policy_model
进行一次梯度更新。这份伪代码简化了分布式计算、API错误处理等工程细节,但完整地保留了DeepResearcher通过强化学习在真实网络环境中进行端到端训练的核心逻辑和创新设计。