游乐游手机版
首页/AI热点日报/热点详情

告别提示工程,DSPy引领未来(下)

类型:热点整理2026-06-23
本文深入解析DSPy框架的核心概念、编程模型与编译器功能,并通过一个简易示例演示其实际应用。内容紧凑,直奔主题。 2 3 DSPy提词器:自动化提示优化与编译器协同机制 在DSPy中,提词器(Teleprompter)充当优化器的角色,通过特定性能指标对DSPy程序模块的提示进行自动优化,并与编译器

本文深入解析DSPy框架的核心概念、编程模型与编译器功能,并通过一个简易示例演示其实际应用。内容紧凑,直奔主题。

告别提示工程,未来属于DSPy(下)

2.3 DSPy提词器:自动化提示优化与编译器协同机制

在DSPy中,提词器(Teleprompter)充当优化器的角色,通过特定性能指标对DSPy程序模块的提示进行自动优化,并与编译器紧密协作,显著提升程序执行的效率与效果。简而言之,它实现了提示的自动化改进。

以最基础的提词器BootstrapFewShot为例:

from dspy.teleprompt import BootstrapFewShot

teleprompter = BootstrapFewShot(metric=dspy.evaluate.answer_exact_match)

DSPy目前已内置五种提词器,各具特色,适用于不同场景:

  • dspy.LabeledFewShot:用于精确控制预测器使用的样本数量(k值)。
  • dspy.BootstrapFewShot:采用引导式启动,像搭积木一样逐步构建高质量示例。
  • dspy.BootstrapFewShotWithRandomSearch:在BootstrapFewShot基础上引入随机搜索,探索更优组合。
  • dspy.BootstrapFinetune:专为编译过程中的模型微调设计,适合追求精细调优的场景。
  • dspy.Ensemble:将多个程序集成并统一输出为单一结果,类似投票机制。

不同提词器在优化成本与输出质量之间各有权衡,选择合适的提词器能让优化工作事半功倍。

3 DSPy编译器:智能优化程序性能

DSPy编译器会在内部跟踪程序的执行路径,并借助提词器(优化器)进行系统性优化,从而全面提升程序性能。该优化过程会根据所选语言模型的规模与特性动态调整策略:

  • 对于大型语言模型(LLMs),编译器会生成少量但高质量的示例提示。
  • 对于规模较小的语言模型,则自动执行微调训练。

换言之,编译器能够智能地将程序模块与最佳的提示、微调、推理及增强策略进行匹配。在后台,它会模拟程序在多种输入下的不同运行版本,并通过引导式学习不断自我完善,最终完美适配你的特定任务。这一过程与训练神经网络有着异曲同工之妙。

此前创建的ChainOfThought模块虽然为语言模型提供了一个良好起点,但往往并非最优提示。如下图所示,DSPy编译器能够自动优化初始提示,彻底省去手动调整提示的繁琐过程——这才是其真正的价值所在。

编译器运行需要以下三个输入:

  • 程序(DSPy模块)
  • 提词器(包含定义的验证指标)
  • 训练样本(少量标注数据)
from dspy.teleprompt import BootstrapFewShot

# 带有问题和答案对的小型训练集
trainset = [dspy.Example(question="What were the two main things the author worked on before college?", 
                         answer="Writing and programming").with_inputs('question'),
            dspy.Example(question="What kind of writing did the author do before college?", 
                         answer="Short stories").with_inputs('question'),
            ...
            ]

# 提词器将引导缺失的标签:推理链和检索上下文
teleprompter = BootstrapFewShot(metric=dspy.evaluate.answer_exact_match)

compiled_rag = teleprompter.compile(RAG(), trainset=trainset)

4 DSPy实战:构建一个简单的RAG(检索增强生成)流程

掌握了核心概念后,下面我们动手构建第一个DSPy流程。检索增强生成(RAG)是目前生成式AI领域的热门技术,以它为起点进行实践再合适不过。

首先,安装DSPy库:

pip install dspy-ai

步骤1:初始化配置

首先配置语言模型(LM)和检索模型(RM)。具体操作如下:

  • 语言模型(LM):选用OpenAI的gpt-3.5-turbo,请提前准备好API密钥。

  • 检索模型(RM):选用Weaviate(一款开源向量数据库)。我们使用示例数据对其进行初始化。

本例数据来自LlamaIndex GitHub仓库(MIT许可)。你也可以使用自己的数据替换。

!mkdir -p 'data'
!wget 'https://raw.githubusercontent.com/run-llama/llama_index/main/docs/examples/data/paul_graham/paul_graham_essay.txt' -O 'data/paul_graham_essay.txt'

接下来,将文档拆分为单独句子并导入数据库。这里使用Weaviate的嵌入式版本,免费且无需注册API密钥。

注意:导入时,每个数据项必须包含名为'content'的属性,这是Weaviate检索的依据。

import wea viate
from wea viate.embedded import EmbeddedOptions
import re

# 以嵌入模式连接到 Wea viate 客户端
client = wea viate.Client(embedded_options=EmbeddedOptions(),
                             additional_headers={
                                "X-OpenAI-Api-Key": "sk-",
                             }
                         )

# 创建 Wea viate 模式
schema = {
   "classes": [
       {
           "class": "MyExampleIndex",
           "vectorizer": "text2vec-openai",
            "moduleConfig": {"text2vec-openai": {}},
           "properties": [{"name": "content", "dataType": ["text"]}]
       }      
   ]
}
    
client.schema.create(schema)

# 将文档分割为单个句子
chunks = []
with open("./data/paul_graham_essay.txt", 'r', encoding='utf-8') as file:
    text = file.read()
    sentences = re.split(r'(?

现在配置全局的语言模型和检索模型:

import dspy
import openai
from dspy.retrieve.wea viate_rm import Wea viateRM

openai.api_key = "sk-"

lm = dspy.OpenAI(model="gpt-3.5-turbo")

rm = Wea viateRM("MyExampleIndex", 
                wea viate_client = client)

dspy.settings.configure(lm = lm, 
                        rm = rm)

步骤2:准备训练数据

接下来收集训练示例。以下是我们手动标注的少量问答对:

trainset = [dspy.Example(question="What were the two main things the author worked on before college?", 
                          answer="Writing and programming").with_inputs('question'),
            dspy.Example(question="What kind of writing did the author do before college?", 
                          answer="Short stories").with_inputs('question'),
            dspy.Example(question="What was the first computer language the author learned?", 
                          answer="Fortran").with_inputs('question'),
            dspy.Example(question="What kind of computer did the author's father buy?", 
                          answer="TRS-80").with_inputs('question'),
            dspy.Example(question="What was the author's original plan for college?", 
                          answer="Study philosophy").with_inputs('question'),]

步骤3:构建DSPy程序模块

首先定义签名GenerateAnswer,描述从问题到答案的转换逻辑:

class GenerateAnswer(dspy.Signature):
    """Answer questions with short factoid answers."""

    context = dspy.InputField(desc="may contain relevant facts")
    question = dspy.InputField()
    answer = dspy.OutputField(desc="often between 1 and 5 words")

随后编写自定义RAG类,继承自dspy.Module。在__init__()中声明所需的子模块,在forward()中定义数据流:

class RAG(dspy.Module):
    def __init__(self, num_passages=3):
        super().__init__()
        self.retrieve = dspy.Retrieve(k=num_passages)
        self.generate_answer = dspy.ChainOfThought(GenerateAnswer)
    
    def forward(self, question):
        context = self.retrieve(question).passages
        prediction = self.generate_answer(context=context, question=question)
        return dspy.Prediction(context=context, answer=prediction.answer)

步骤4:编译与优化模型

最后定义提词器并编译程序,该过程会更新ChainOfThought模块所使用的提示:

from dspy.teleprompt import BootstrapFewShot

teleprompter = BootstrapFewShot(metric=dspy.evaluate.answer_exact_match)

compiled_rag = teleprompter.compile(RAG(), trainset=trainset)

调用编译后的RAG流程进行推理:

pred = compiled_rag(question = "What programming language did the author learn in college?")

你可以评估输出结果,并反复迭代优化,直至达到满意的性能。通过这一完整流程,原本繁琐的手工提示工程工作将完全交由DSPy自动完成。

来源:https://www.53ai.com/news/tishicijiqiao/2024090124159.html

相关热点

继续查看同栏目近期热点。

延伸阅读

补充最近整理过的热点入口。