原文链接:https://weaviate.io/blog/hurricane-generative-feedback-loops

早在2023年5月,我们发布了生成式反馈循环[1]的初步愿景,我们将其定义为将生成式AI系统的输出保存回数据库以供将来使用。此后,我们将实验从Airbnb房源扩展到了亚马逊产品[2],甚至在Snowpark容器服务[3]中运行生成式反馈循环的每个组件。这两个应用程序都展示了生成式AI增强我们数据的能力。随着DSPy的出现,我们现在正在进入一个使用生成式AI系统进行控制的新时代,并能够创建更引人注目的生成式反馈回路示例。
当我们最初发布对生成式反馈循环的预测时,我们使用了Ben Thompson的聚合理论[4]来描述这项技术的一些影响。聚合理论描述了"在用户体验上获胜的公司如何产生一个良性循环,其中对消费者/用户的所有权吸引供应商,从而改善用户体验"。我们的结论是,"LLM提供了加速聚合理论所描述的良性循环的机会,通过将传统上提供出色用户体验所需的人力商品化"。
在Weaviate,我们致力于为我们的开发者提供出色的用户体验。我们为此所做的主要工作之一是撰写博客文章,阐明关键概念并帮助开发人员使用Weaviate进行构建。本文将向您介绍我们weaviate-tutorials
合集的新成员,Hurrican
e。受斯坦福大学STORM[5]的启发,Hurricane利用来自Arize、DSPy、OpenAI、Weaviate和You的技术来创作新的Weaviate博客文章,并将这些生成的博客反馈给Weaviate。Hurricane减轻了提供优质博客阅读用户体验所需的人力,使其适应Weaviate开发者的特定兴趣和问题。
本文包含两个关键部分: 1.Hurricane代码解释[6] 2.优化Hurricane[7]
第一部分:Hurricane代码解释
受Erika最初使用DSPy写博客文章的实验[8]和斯坦福大学的STORM的启发,我们开始明白,我们可以用DSPy构建全新类型的生成式AI应用程序。正如ChatGPT、Perplexity、Le Chat和Weaviate的Verba[9]等广受欢迎的AI产品所示,将用户界面设计置于开发的核心,可以极大地促进新技术的采用。
用户输入他们想要写博客文章的问题。 Hurricane确认请求并在写作时传递其进度。 Hurricane向用户返回一篇博文,并更新Weaviate中AI生成的博文计数器。
正如Arize Phoenix[10]所说的那样,使用GPT-3.5-Turbo运行Hurricane大约需要45秒才能将问题转化为博文。这给用户体验设计带来了重大挑战。因此,我们认为中间进度流或"思考"将有助于在长时间运行的过程中保持用户的参与度。我们看到ChatGPT发布了几个用户体验功能,我们认为这些功能应该得到赞美并整合到未来的系统设计中:停止生成
、编辑过去的消息
和对话历史
。这些交互有助于人类通过AI系统实现他们想要的目标。生成式反馈循环为增强这些用户体验提供了重大机会,我们只是通过Hurricane的设计初步尝试。
现在,我们将转向Hurricane的后端以及我们如何使用DSPy对程序进行编排。从程序和签名设计开始,DSPy编程模型为定义提示及其各自的输入和输出字段提供了出色的开发人员体验。DSPy进一步将这些程序与下一代优化器接口,我们将在本文后面讨论。DSPy编程模型由定义任务指令以及输入和输出字段的签名组成,以及实现签名并描述它们如何在模块之间交换消息的模块。Hurricane由5个签名组成:Question2BlogOutline、Topic2Pargraph、BoldPrediction、WeaviateRelevance和TitleAndTakeaways。签名还大大促进了带有提示的代码库的组织,如此处[10]的hurricane_signatures.py
所示。
class Question2BlogOutline(dspy.Signature):
"""Your task is to write a Weaviate blog post that will help answer the given question.\nPlease use the contexts from a web search and published Weaviate blog posts to evaluate the structure of the blog post."""
question = dspy.InputField()
blog_context = dspy.InputField()
web_context = dspy.InputField()
blog_outline = dspy.OutputField(desc="A list of topics the blog will cover. IMPORTANT!! This must follow a comma separated list of values!")
introduction_paragraph = dspy.OutputField(desc="An introduction overview of the blog post that previews the topics and presents the question the blog post seeks to answer.")
class Topic2Paragraph(dspy.Signature):
"""Please write a paragraph that explains a topic based on contexts from a web search and blog posts from an authoritative source. You are also given the original question that inspired research into this topic, please try to connect your review of the topic to the original question."""
topic = dspy.InputField(desc="A topic to write a paragraph about based on the information in the contexts.")
original_question = dspy.InputField(desc="The original question that inspired research into this topic.")
web_contexts = dspy.InputField(desc="contains relevant information about the topic from a web search.")
blog_contexts = dspy.InputField(desc="contains relevant information about the topic from the published Weaviate blogs.")
paragraph = dspy.OutputField()
class BoldPrediction(dspy.Signature):
"""Please review this blog post and propose a bold prediction about it's content."""
blog = dspy.InputField()
bold_prediction = dspy.OutputField(desc="A bold prediction about it's content.")
class WeaviateRelevance(dspy.Signature):
"""Please review this blog post and describe why its content and the claims it's making are relevant for the development of the Weaviate Vector Database. You are given additional contexts describing what Weaviate is and some aspects of its technology."""
blog_contexts = dspy.InputField(desc="Content describing what Weaviate is")
blog_post = dspy.InputField()
weaviate_relevance = dspy.OutputField()
class TitleAndTakeaways(dspy.Signature):
"""Write a title and key takeaways for a blog post given the blog post and the original question it sought to answer as input and a bold prediction the author discovered after conducting initial research on the topic."""
blog = dspy.InputField()
original_question = dspy.InputField()
title = dspy.OutputField()
key_takeaways = dspy.OutputField(desc="Key takeaways from the article. IMPORTANT!! This must follow a comma separated list of values!")
然后我们可以通过定义DSPy程序Hurricane
来连接这些签名如何处理输入。与以前的自动化浪潮类似,人工智能的最新进展允许我们将思维抽象为我们试图实现的目标的高层结构,并将繁琐的细节留给自动化系统。我们不关注博客文章内容的特定细节,而是考虑博客写作任务的结构应该是什么样的。在Hurricane中,我们将博客写作任务分解为 (1) 研究和写出大纲,(2) 对大纲中的每个主题进行进一步研究和撰写,(3) 根据迄今为止的写作形成对未来的大胆预测,(4) 写下这个主题与Weaviate的相关性,最后(5) 为博客文章写一个标题和关键要点。下图显示了组件之间如何连接以及计算的哪些部分可以并行化。

在DSPy中连接这些组件的代码如下所示:
import dspy
from hurricane_signatures import Question2BlogOutline, Topic2Paragraph, BoldPrediction, WeaviateRelevance, TitleAndTakeaways
from utils import format_weaviate_and_you_contexts
from utils import format_blog_draft, format_blog_post, BlogPost
class Hurricane(dspy.Module):
def __init__(self, you_rm):
self.question_to_blog_outline = dspy.ChainOfThought(Question2BlogOutline)
self.topic_to_paragraph = dspy.ChainOfThought(Topic2Paragraph)
self.bold_prediction = dspy.ChainOfThought(BoldPrediction)
self.weaviate_relevance = dspy.ChainOfThought(WeaviateRelevance)
self.title_and_key_takeaways = dspy.ChainOfThought(TitleAndTakeaways)
self.you_rm = you_rm
def forward(self, question):
blog_container = BlogPost()
blog_contexts = dspy.Retrieve(k=5)(question).passages
web_contexts = self.you_rm(question)
blog_contexts, web_contexts = format_weaviate_and_you_contexts(blog_contexts, web_contexts)
question_to_blog_outline_outputs = self.question_to_blog_outline(question=question, blog_context=blog_contexts, web_context=web_contexts)
blog_container.outline = question_to_blog_outline_outputs.blog_outline
parsed_blog_outline = blog_container.outline.split(",")
blog_container.introduction_paragraph = question_to_blog_outline_outputs.introduction_paragraph
for topic in parsed_blog_outline:
blog_contexts = dspy.Retrieve(k=5)(topic).passages
web_contexts = self.you_rm(topic)
blog_contexts, web_contexts = format_weaviate_and_you_contexts(blog_contexts, web_contexts)
blog_container.evidence_paragraphs.append(self.topic_to_paragraph(topic=topic, original_question=question, web_contexts=web_contexts, blog_contexts=blog_contexts).paragraph)
blog = format_blog_draft(blog_container)
blog_container.bold_prediction = self.bold_prediction(blog=blog).bold_prediction
blog_contexts = dspy.Retrieve(k=8)("What technology does Weaviate build?").passages
blog_contexts = "".join(blog_contexts)
blog_container.weaviate_relevance = self.weaviate_relevance(blog_contexts=blog_contexts, blog_post=blog).weaviate_relevance
title_and_takeaways = self.title_and_key_takeaways(blog=blog, original_question=question)
blog_container.title = title_and_takeaways.title
blog_container.takeaways = title_and_takeaways.key_takeaways
final_blog = format_blog_post(blog_container)
return dspy.Prediction(blog=final_blog)
我们使用此程序结构进行编译,但在推理时,我们将每个组件分离到自己的API中。这可以通过将程序状态加载到每个组件来完成,如下所示:
compiled_hurricane = Hurricane(you_rm)
compiled_hurricane.load("compiled_hurricane.json")
question_to_blog_outline = compiled_hurricane.question_to_blog_outline
topic_to_paragraph = compiled_hurricane.topic_to_paragraph
bold_prediction = compiled_hurricane.bold_prediction
weaviate_relevance = compiled_hurricane.weaviate_relevance
title_and_key_takeaways = compiled_hurricane.title_and_key_takeaways
在回到Web应用程序代码之前,我们想强调LLM程序设计的自我发现[11]。人类程序设计需要多少仍然是一个悬而未决的问题。例如,将以下提示词发给Claude 3会产生与我们上面展示的非常相似的程序架构。本着与Gorilla LLMs[12]相似的精神,我们也可以给LLM关于DSPy Python语法的背景信息,它将生成一个可执行的程序。
❝你能帮我把一个任务分解成子任务吗?任务是接受一个问题并写一篇回答它的博客文章,提供有关该主题的更多背景信息,寻找该主题的细微差别,例如未回答的问题或大胆的预测,并将该主题与Weaviate Vector Database的相关性联系起来。请将每个子任务格式化为一个
Signature
,其中包含任务描述以及输入和输出字段。请描述每个子任务如何处理来自前一个子任务的输出,以及可以在Module
中并行化子任务的位置。
有状态AI
回到我们的Web应用程序,围绕DSPy和LLM编程最有趣的问题之一是:如何在生产中提供DSPy程序?随着检索增强生成(RAG)的广泛采用,Weaviate联合创始人Bob van Luijt解释了Weaviate帮助开发人员构建有状态AI的使命。在客户端-服务器软件设计中,状态管理涉及在服务器和客户端之间维护和同步应用程序的数据。服务器通常处理中央状态,例如应用程序或会话数据,以及在多个客户端之间共享的资源,例如缓存、消息队列或文件存储。客户端通过向服务器发送请求与中央状态进行交互,服务器然后处理请求,在必要时更新中央状态,并将响应发送回客户端。
为了促进LLM应用程序中的状态管理,Weaviate开发了generative-search[13],其中包含与Cohere、Google、Mistral、OpenAI、Bedrock和Anyscale的集成。生成式搜索将检索和推理管理结合到服务器上编排的单个API中。我们目前正在研究进一步改进这个产品的方法,并帮助开发人员管理其LLM应用程序中的状态。Hurricane目前使用由一系列客户端-服务器调用组成的生成式反馈循环,通过将数据插入Weaviate并使用会话ID访问它来持久化状态。单个LLM调用(我们发送提示并接收文本)是无状态的,但当我们使用来自检索或先前LLM调用的数据扩展LLM调用时,例如从Question2BlogOutline
到Topic2Paragraph
的交接,调用现在是有状态的。
Hurricane中的有状态处理按如下方式编排:
当单击提交按钮时,我们向服务器发送请求,并在Weaviate中创建一个新的 Blog
对象实例,返回UUID作为会话ID,并为Hurricane的中间状态处理提供键值查找。
const handleClick = async () => {
try {
setThoughts(prevThoughts => ["Received question: " + String(inputValue)]);
const createSessionResponse = await axios.post('http://localhost:8000/create-session');
const sessionId = String(createSessionResponse.data.session_id);
} catch (error) {
console.error('Error', error);
}
}
然后我们使用5个API处理问题: /question-to-blog
、/topic-to-paragraph
、/bold-prediction
、/weaviate-relevance
和/finish-blog
。每个端点都使用Weaviate通过提供sessionId
来保存和加载中间状态,例如:
@app.post("/weaviate-relevance")
async def weaviate_relevance_generator(request: SessionRequest):
sessionId = request.sessionId
weaviate_gfl_client = weaviate.connect_to_local()
weaviate_blog_collection = weaviate_gfl_client.collections.get("Blog")
blog_container = BlogPost()
saved_blog_properties = weaviate_blog_collection.query.fetch_object_by_id(sessionId)
for key in saved_blog_properties.properties:
setattr(blog_container, key, saved_blog_properties.properties[key])
blog = format_blog_draft(blog_container)
blog_contexts = dspy.Retrieve(k=5)("What technology does Weaviate build?").passages
blog_contexts = "".join(blog_contexts)
weaviate_relevance_response = weaviate_relevance(blog_contexts=blog_contexts, blog_post=blog).weaviate_relevance
weaviate_blog_collection.data.update(
uuid=sessionId,
properties={
"weaviate_relevance": weaviate_relevance_response
}
)
thoughts = "Researched why this topic is relevant to Weaviate."
return {"thoughts": thoughts}
注意,我们还使用Pydantic模型来格式化博客文章的中间状态为特定输入的博客草稿,以及将最终结果返回给JavaScript组件。Pydantic是Python中的一个库,提供对严格类型的对象的访问,例如Golang中的struct
。
from pydantic import BaseModel
class BlogPost(BaseModel):
question: Optional[str] = None
title: Optional[str] = None
introduction_paragraph: Optional[str] = None
outline: Optional[str] = None
evidence_paragraphs: Optional[List[str]] = []
bold_prediction: Optional[str] = None
weaviate_relevance: Optional[str] = None
takeaways: Optional[List[str]] = []
我们从Weaviate加载最终状态,将其传递到Pydantic模型中,并将其发送到前端,以使用 Blogpost.js
模板进行渲染:
import React from 'react';
const BlogPost = ({ blogPost }) => {
if (!blogPost) {
return null;
}
return (
<div class="blogstyling">
{blogPost.title && <h1>{blogPost.title}</h1>}
{blogPost.introduction_paragraph && <p>{blogPost.introduction_paragraph}</p>}
{blogPost.evidence_paragraphs && blogPost.evidence_paragraphs.length > 0 && (
<div>
{blogPost.evidence_paragraphs.map((paragraph, index) => (
<p key={index}>{paragraph}</p>
))}
</div>
)}
{blogPost.bold_prediction && (
<div>
<h3>Bold Prediction</h3>
<p>{blogPost.bold_prediction}</p>
</div>
)}
{blogPost.weaviate_relevance && (
<div>
<h3>Relevance to Weaviate</h3>
<p>{blogPost.weaviate_relevance}</p>
</div>
)}
{blogPost.takeaways && blogPost.takeaways.length > 0 && (
<div>
<h3>Takeaways from {blogPost.title}:</h3>
<ul>
{blogPost.takeaways.map((takeaway, index) => (
<li key={index}>{takeaway}</li>
))}
</ul>
</div>
)}
</div>
);
};
export default BlogPost;
我们相信DSPy程序在微服务架构设计方面还有很多机会。例如,作为下一步,我们可以并行化对Topic2Paragraph
的5个调用,因为它们彼此不依赖。然后,我们将等待将证据段落同步到博客草稿中,然后继续并行化BoldPrediction
和WeaviateRelevance
。在这个领域有许多有趣的工作,我们强烈建议感兴趣的读者查看Santhanam等人的ALTO[14]。如下所示,ALTO通过集成流式结构化输出解析来进一步加速并行处理,从而进一步推进LLM程序设计的前沿。这个主题在我们的Weaviate播客与Jason Liu[15]中也有很多讨论。

在许多其他情况下,我们可能希望将DSPy程序的组件分成多个API。例如,在优化期间,我们可能有一个打包在一个容器中的8层程序要优化,然后在其他容器中有一个3层度量程序或7层MIPRO优化器。这提高了规模化时的吞吐量和资源分配。正如我们在Weaviate的生成式反馈循环中所展示的那样,这对于将中间状态保存供将来使用,或者在程序崩溃并需要从停止的地方继续时也极大地有帮助。想象一下非常复杂的系统,我们还可以使用条件路由重用程序的某些部分。此外,我们可以想象未来的系统由封闭API背后的LLM和自托管模型共同组成。这可以促进在内部处理包含敏感信息的程序部分,以及在为特定任务提供较小的fine-tuned模型时的成本效率。我们鼓励感兴趣的读者查看Weaviate模块系统,以更好地了解未来几个月Weaviate开发团队的预期。我们对generative-search APIs的新解耦改进[16]感到非常兴奋,这将在同时促进轻松的模型切换,但从长远来看,使Weaviate对从RAG到生成式反馈循环和复合AI系统[17]的各种LLM处理更加模块化。
第二部分:Hurricane优化
希望您已经对DSPy编程模型印象深刻,并且很高兴使用此框架编写任务描述,定义LLM调用的输入和输出字段,并在程序的forward
传递中编排系统逻辑。但是,DSPy的新机会并不止于此,事实上,我们只是触及了表面!在DSPy的后端,我们有一个全新的优化器范式,也称为teleprompters或compilers。DSPy优化器使用新颖的算法来找到最佳的任务描述、用于few-shot上下文学习或使用梯度下降进行微调的输入-输出示例,并且随着Self-Discover的出现,也许还包括程序本身的结构[18]。
DSPy最近推出了两个新的优化器,COPRO和MIPRO[19]。吸引我们参与这个项目的最大机会之一是更好地理解这些新优化器如何处理多层程序。在本文中,我们使用了COPRO指令优化到BootstrapFewShot示例采购的流水线。
COPRO是一个非常有趣的任务指令优化器,让人联想到Google DeepMind的Promptbreeder[20]。COPRO首先提出表达任务的替代方式。例如,我们首先用Your task is to write an optimized description of a task
提示LLM,它可能会将"please rerank these documents according to their relevance to a query"转换为"optimize and reorganize a collection of documents by arranging them in order of their significance and applicability in response to a specific search query"。
然后,COPRO评估每个重写描述的性能,并使用进化优化算法中常见的有趣交叉步骤编写新的候选项。COPRO将描述及其各自性能的breadth
超参数作为输入,并使用此信息提出进一步重写的描述。这将继续进行depth
超参数次数的迭代。将COPRO应用于Hurricane会导致最初提示到优化提示的以下转换。
| 签名 | 初始提示 | COPRO 优化提示 |
|---|---|---|
| Blog2Outline | 你的任务是撰写一篇 Weaviate 博客文章,帮助回答给定的问题。请利用网络搜索和已发布的 Weaviate 博客文章的背景来评估博客文章的结构。 | 开始进行彻底的研究,收集来自权威来源的相关信息以回答提供的问题。分析以前 Weaviate 博客文章中使用的结构和语言,以保持一致性。考虑包含图像或图表等可视化内容以增强内容。 |
| Topic2Paragraph | 请撰写一段解释一个主题的段落,基于网络搜索和权威来源的博客文章的背景。你还得到了启发研究该主题的原始问题,请尝试将你对该主题的评论与原始问题联系起来。 | 研究、整合见解、分析各种案例研究,并总结信息,以阐明围绕感兴趣主题的具体背景。确保引用权威来源支持你的结论,并尝试将你的全面分析与引发你调查的初始问题联系起来。 |
| BoldPrediction | 请审查这篇博客文章,并对其内容提出大胆的预测。 | 分析文章,与当前趋势建立相关联系,并对其主题内容提出创新的预测。 |
| WeaviateRelevance | 请审查这篇博客文章,并描述其内容及所作声明对 Weaviate 向量数据库的发展为何具有相关性。你将获得描述 Weaviate 是什么以及其技术某些方面的额外背景。 | 请审查这篇博客文章,并描述其内容及所作声明对 Weaviate 向量数据库的发展为何具有相关性。你将获得描述 Weaviate 是什么以及其技术某些方面的额外背景。 |
| TitleAndTakeaways | 针对博客文章和其旨在回答的原始问题提供一个标题和要点。作者在对该主题进行初步研究后发现了一个大胆的预测,请提供一个基于初步研究的大胆预测。 | 根据原始问题和主要发现提供博客文章的简明摘要,然后重点突出基于初步研究的大胆预测。 |
然后,我们将这些新签名与BootstrapFewShot
编译器堆叠在一起,该编译器使用新签名运行程序跟踪,提供输入-输出示例以更好地控制系统。在我们的实验中,我们为Hurricane的每个5个组件引导2个示例。
DSPy团队最近推出了他们最新、最伟大的优化器MIPRO,这标志着他们从COPRO毕业并迈入新的阶段。MIPRO的全称是“多提示指令提议优化器”,通过添加数据集总结器和贝叶斯优化提议指令和示例,扩展了自动提示优化。我们从Arize Phoenix中获得了巨大的价值,帮助我们理解编译过程。像COPRO和MIPRO这样的优化器会多次调用LLMs来优化LLMs,而Phoenix的追踪功能非常有洞察力,有助于跟踪工作进展情况!
希望这能让您很好地初步了解这些优化器的工作原理。更深入的探讨有点超出了这篇博文的范围。如果有兴趣进一步讨论这些内容,我们强烈建议加入DSPy discord[21]!
一旦我们有了一个编译好的程序,下面的简短代码片段说明了如何保存和加载一个编译的DSPy程序:
compiled_hurricane.save(“compiled_hurricane.json”)
hurricane = Hurricane()
hurricane.load(“complied_hurricane.json”)
DSPyOps
DevOps是软件工程团队中一个涵盖范围最广的角色,需要从生产日志监控到持续集成和部署新软件等多方面的专业知识。随着AI原生应用程序引发软件设计的巨大变革,MLOps应运而生,用于描述机器学习系统独特的DevOps挑战。MLOps涵盖了许多工程和研究领域,包括实验跟踪、超参数调整、持续训练、模型版本控制、数据漂移检测等。随着LLMs的兴起,MLOps逐渐演变为LLMOps,几乎所有概念都在过渡中得以保留,但重点从持续训练转移到了输入输出记录和检索监控。
我们认为DSPy具有足够的颠覆性,值得采用下一个Ops命名法,即DSPyOps。与LLMOps的关键演变之处在于我们将持续训练和模型版本控制的重点从MLOps中重新强调出来。然而,与LLMOps类似,DSPyOps也非常注重日志记录和调用监控。
我们看到对LLM-现在是DSPy- Ops最强大的工具之一是Arize AI,进一步提供了一个名为Phoenix
的开源产品。我们发现Phoenix对于使用DSPy构建非常有帮助。Phoenix将LLMs的调用记录为JSON格式,让您可以检查输入和输出。Phoenix进一步将跟踪包装在其程序结构中,让您可以检查每个Hurricane程序中对Hurricane.forward()
的调用的每个中间输入和输出。Phoenix记录每次调用的延迟,并将结果总结为P50和P99延迟!
正如之前讨论的那样,这对于找出由多个LLMs、程序和每个程序内的层组成的DSPy程序中存在瓶颈的地方可能会带来极大的洞察力!
跟踪生成性反馈循环的进展与Weaviate在监控导入到Weaviate或在集群之间移动数据方面所做的工作非常相似。我们与Prometheus指标、Grafana仪表板和Datadog的集成和合作使我们能够了解Weaviate使用了多少内存,导入单个对象或对象批次的时间,以及查询延迟。随着生成性反馈循环填充Weaviate内部的数据,我们将需要使用相同的工具进行监控和可观察性。要了解更多关于Weaviate和Datadog的信息,请注册参加Erika Cardenas主持的网络研讨会[22]!
DSPyOps与最近关于LLMOps的讨论确实有所不同,因为我们增加了优化组件。因此,问题变成了:如何监控性能并重新运行优化?应该持续运行哪种优化?我们认为MIPRO优化器集成数据集分析将对抗潜在的数据集或分布变化,有助于解决持续学习问题。另一个突出问题是:如何在生产环境中更新DSPy程序?正如之前所示,我们可以通过加载编译参数发送到系统的JSON文件来更新DSPy程序。这对于调用黑匣子LLM API的系统非常有效,但更新自托管的精细调整LLMs将需要更深入的了解。
结束语
希望这个使用生成式 AI 撰写博客文章的例子能进一步激发生成式反馈循环的可能性!这描述了将生成式人工智能系统产生的数据反馈到数据库中以供将来使用。生成反馈循环可以通过多种方式增强博客文章的体验,从生成我们探索过的新帖子,到建议对现有帖子进行编辑,或对帖子所涵盖的内容进行元分析等等。
我们相信,用于博客文章写作的生成反馈循环的下一步将是为Hurricane提供内在动力。目前,Hurricane 只会在人类启动应用程序并输入问题或主题时才写博客文章。但是,Hurricane 可能会根据现有博客文章的上下文和问题进行提示,例如“这篇博文进一步激发了您的兴趣?我们目前撰写的博客文章平均每篇博客文章大约有 15,500 个代币块。想象一下,我们写了 100 篇合成博客文章,现在我们的矢量数据库中有 1,500 个块。通过将这些数据与荟萃分析等其他处理联系起来,编写代码或额外的文档可能会导致大多数生成式 AI 应用程序的数据集大小爆炸式增长。
然而,Hurricane 还没有准备好实现这一潜力。目前,生成具有 GPT-4 等大容量模型的博客文章的成本太高。因此,我们相信效率优化,例如使用DSPy编译器来调整Mistral 7B,或微调Gemma 2B,将非常有价值,并将我们带入一个每个人都拥有数百万甚至数十亿个数据对象的未来。
Hurricane只是一个开始。随着我们继续开发和完善这些技术,我们设想了一个未来,生成反馈循环可以自主创建大量有用的内容,以适应每个人的特定需求和兴趣。通过将这些生成的内容反馈到系统中,我们可以创建一个不断增长的知识库,并不断更新和完善。要实现这一愿景,就需要在及时工程、模型优化和用户体验设计等领域进行持续的研究和开发。它还需要仔细考虑成本效益、数据质量和道德内容生成。
相关链接
[1]https://weaviate.io/blog/generative-feedback-loops-with-llms
[2]https://medium.com/@iamleonie/recreating-amazons-new-generative-ai-feature-product-review-summaries-50640e40872a
[3]https://weaviate.io/blog/generative-feedback-loop-with-weaviate-and-spcs#implementing-a-generative-feedback-loop-with-weaviate
[4]https://stratechery.com/2015/aggregation-theory/
[5]https://arxiv.org/abs/2402.14207
[6]https://weaviate.io/blog/hurricane-generative-feedback-loops#part-1-hurricane-code-explained
[7]https://weaviate.io/blog/hurricane-generative-feedback-loops#part-2-hurricane-optimization
[8]https://www.youtube.com/watch?v=ickqCzFxWj0
[9]https://github.com/weaviate/Verba
[10]https://docs.arize.com/phoenix
[11]https://arxiv.org/pdf/2402.03620.pdf
[12]https://weaviate.io/blog/weaviate-gorilla-part-1
[13]https://weaviate.io/developers/weaviate/search/generative
[14]https://arxiv.org/pdf/2403.04311.pdf
[15]https://www.youtube.com/watch?v=higlHgYDc5E
[16]https://github.com/weaviate/weaviate/issues/3364
[17]https://bair.berkeley.edu/blog/2024/02/18/compound-ai-systems/
[18]https://twitter.com/ecardenas300/status/1769396057002082410
[19]https://twitter.com/kristahopsalong/status/1766166198079889737
[20]https://arxiv.org/pdf/2309.16797.pdf
[21]https://discord.gg/zqcyX9TN4Q
[22]https://www.datadoghq.com/partner/weaviate-q1/?utm_source=partner&utm_medium=organic-email&utm_term=p&utm_campaign=webinar-202403weaviate




