跳转到主要内容

TL;DR:我们正在引入一种新型的代理执行器,我们称之为“计划和执行”。这是为了与我们以前支持的代理类型形成对比,我们称之为“Action”代理。计划和执行代理在很大程度上受到了BabyAGI和最近的计划和解决论文的启发。我们认为Plan and Execute非常适合更复杂的长期规划,但代价是需要调用更多的语言模型。我们正在将其初始版本放入实验模块,因为我们预计会有快速的变化。

链接:

到目前为止,LangChain中的所有代理都遵循ReAct文件开创的框架。让我们称之为“行动特工”。这些算法可以大致用以下伪代码表示:

  • 接收到一些用户输入
  • 代理决定使用哪种工具(如果有的话),以及该工具的输入应该是什么
  • 然后用该工具输入调用该工具,并记录观察结果(这只是用该工具输出调用该工具的输出)
  • 工具、工具输入和观察的历史记录被传递回代理,它决定下一步要采取的步骤
  • 重复此操作,直到代理决定不再需要使用工具,然后直接响应用户。

到目前为止,这种风格一直很有效,但有几件事正在发生变化,这在这种算法中出现了一些裂缝:

  • 用户目标变得越来越复杂

  • 开发人员和组织开始在生产中依赖代理

这具有双重效果,即希望代理系统能够处理更复杂的请求,同时也更可靠。这两个因素结合在一起,迅速导致提示大小增加:

  • 随着目标越来越复杂,越来越多的过去历史被包括在内,以使代理专注于最终目标,同时也允许它记住和推理以前的步骤
  • 随着开发人员试图提高可靠性,他们包含了更多关于如何使用工具的说明

在使用大多数语言模型时,对越来越复杂的能力和越来越高的可靠性的需求导致了问题。

计划和执行实施

在这种情况下,我们看到了一种新型的代理框架的出现。这些代理框架试图将更高级别的计划与短期的执行分开。具体来说,他们首先计划要采取的步骤,然后迭代执行这些步骤。当然,这个核心算法有一些有趣的变体(我们可以稍后讨论)。这些代理的伪代码,我们称之为“计划和执行”代理,看起来像:

计划要采取的步骤

  • 对于分步:确定完成该步骤的适当工具或其他最佳行动方案
  • 这是用Python和TypeScript实现的核心代理框架。这个代理框架依赖于两件事:一个计划器和一个执行器。

让我们先谈谈计划器。这几乎总是应该是一个语言模型。这将利用语言模型的推理能力来计划要做什么并处理歧义/边缘情况。我们可以在末尾添加一个输出解析器,将原始LLM输出解析为字符串列表(每个字符串都是一个步骤)。

现在我们来谈谈执行器。在我们最初的实现中,我们已经将其作为一个Action Agent。这允许执行器代理接受一个高级别的目标(一个步骤),并找出使用哪些工具来实现这一目标(可以在一两个步骤中完成)。

这种方法有几个好处。它将计划与执行分离开来——这允许一个LLM专注于计划,另一个专注于执行。这使得在两个方面都具有更高的可靠性。这也使得将来更容易将这些组件换成更小的微调模型。这种方法的主要缺点是需要更多的电话。然而,由于关注点的分离,我们希望这些呼叫可以针对更小(因此更快、更便宜)的型号。

未来发展方向

我们认为这只是计划和执行代理的开始。未来的发展方向包括:

  • 更好地支持长序列的步骤。现在,前面的步骤以列表的形式传递——随着计划步骤越来越长,我们希望将其存储在向量库中并检索中间步骤
  • 重新制定计划。现在一开始就有一个计划步骤,但后来再也没有重新考虑过。我们很可能希望有一些机制来重新审视和调整计划,无论是每一步还是根据需要。
  • 评价目前,这些改进大多是理论上的,或者至少没有基准。我们希望有更严格的方法来评估代理框架。
  • 执行链的选择。现在,只有一个执行链。很容易出现需要多个执行链的情况,规划器可以指定要使用哪一个。例如,如果您有一个针对网络研究优化的执行链,一个用于分析等。

应该注意的是,对于这些未来的许多方向,我们可以从现有的工作中获得灵感。例如,BabyAGI已经使用向量库来存储中间步骤,并重新制定每次迭代的计划。计划和解决方案论文通过基准对产出进行了更严格的评估。

结论

看到这种新的代理模式在BabyAGI中出现,我们真的很兴奋(几周前,我们在帖子中强调了这一点)。我们同样兴奋地看到“计划和解决方案”论文作为对类似想法的严格评估而出现。我们期待着看到Plan and Execute方法的发展——在这里(Python)或这里(JS)尝试一下。