斯坦福NLP实验室重磅开源:DSPy,让大模型开发更简单,附代码

科技   2024-10-23 10:15   中国香港  

DSPy: 编程而非提示工程的基础模型框架

DSPy是斯坦福大学自然语言处理实验室开发的一个开源框架,旨在为基础模型提供一种新的编程范式,取代传统的提示工程方法。

DSPy的核心理念

DSPy的核心理念是"编程而非提示工程"(Programming—not prompting)。

它提供了一套声明式的API,让开发者可以像编写普通Python程序一样构建复杂的语言模型应用,而无需手动编写和调试繁琐的提示词。

DSPy引入了两个关键概念:

  1. 签名(Signature):用于声明性地指定语言模型输入输出的行为。

  2. 优化器(Optimizer,原名Teleprompter):自动优化程序中的提示词或模型权重。

DSPy的主要特性

  • 提供了通用的模块(如ChainOfThought、ReAct等),可以替代特定的提示工程技巧。

  • 引入了优化器,可以自动生成和选择有效的提示词。

  • 支持在Python控制流中自由使用DSPy模块。

  • 只需少量标注数据即可工作,框架会自动引导生成中间标签。

  • 可以针对不同的语言模型、数据集和管道自动优化提示词或微调权重。

使用DSPy的优势

使用DSPy进行开发相比传统方法有以下优势:

  1. 更加模块化和可维护的代码结构。

  2. 无需手动编写和维护复杂的提示词字符串。

  3. 当更改数据、流程或目标模型时,可以自动重新优化提示词。

  4. 可以更专注于系统设计,而非繁琐的提示词工程。

安装和使用

可以通过pip安装DSPy:

pip install dspy-ai

实践示例

让我们通过两个简单的示例来展示DSPy的使用方法。

示例1: 最小工作示例

这个示例使用GSM8K数据集和OpenAI的GPT-3.5-turbo模型来演示DSPy的基本用法。

  1. 首先,我们设置环境并导入必要的模块:
import dspy
from dspy.datasets.gsm8k import GSM8K, gsm8k_metric

# 设置语言模型
turbo = dspy.OpenAI(model='gpt-3.5-turbo-instruct', max_tokens=250)
dspy.settings.configure(lm=turbo)

# 加载GSM8K数据集
gsm8k = GSM8K()
gsm8k_trainset, gsm8k_devset = gsm8k.train[:10], gsm8k.dev[:10]
  1. 定义一个使用ChainOfThought模块的自定义程序:
class CoT(dspy.Module):
    def __init__(self):
        super().__init__()
        self.prog = dspy.ChainOfThought("question -> answer")
    
    def forward(self, question):
        return self.prog(question=question)
  1. 使用BootstrapFewShot优化器编译模型:
from dspy.teleprompt import BootstrapFewShot

config = dict(max_bootstrapped_demos=4, max_labeled_demos=4)
teleprompter = BootstrapFewShot(metric=gsm8k_metric, **config)
optimized_cot = teleprompter.compile(CoT(), trainset=gsm8k_trainset)
  1. 评估模型性能:
from dspy.evaluate import Evaluate

evaluate = Evaluate(devset=gsm8k_devset, metric=gsm8k_metric, num_threads=4, display_progress=True, display_table=0)
evaluate(optimized_cot)
  1. 查看模型的最近生成:
turbo.inspect_history(n=1)

示例2: RAG (检索增强生成)

这个示例展示了如何使用DSPy构建一个RAG (Retrieval-Augmented Generation) 管道。

  1. 配置语言模型和检索模型:
import dspy

turbo = dspy.OpenAI(model='gpt-3.5-turbo')
colbertv2_wiki17_abstracts = dspy.ColBERTv2(url='http://20.102.90.50:2017/wiki17_abstracts')

dspy.settings.configure(lm=turbo, rm=colbertv2_wiki17_abstracts)
  1. 加载数据集:
from dspy.datasets import HotPotQA

dataset = HotPotQA(train_seed=1, train_size=20, eval_seed=2023, dev_size=50, test_size=0)
trainset = [x.with_inputs('question'for x in dataset.train]
devset = [x.with_inputs('question'for x in dataset.dev]
  1. 定义签名和RAG管道:
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")

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)
  1. 编译和优化RAG程序:
from dspy.teleprompt import BootstrapFewShot

def validate_context_and_answer(example, pred, trace=None):
    answer_EM = dspy.evaluate.answer_exact_match(example, pred)
    answer_PM = dspy.evaluate.answer_passage_match(example, pred)
    return answer_EM and answer_PM

teleprompter = BootstrapFewShot(metric=validate_context_and_answer)
compiled_rag = teleprompter.compile(RAG(), trainset=trainset)
  1. 执行和评估RAG管道:
my_question = "What castle did David Gregory inherit?"
pred = compiled_rag(my_question)

print(f"Question: {my_question}")
print(f"Predicted Answer: {pred.answer}")
print(f"Retrieved Contexts (truncated): {[c[:200] + '...' for c in pred.context]}")

from dspy.evaluate.evaluate import Evaluate

evaluate_on_hotpotqa = Evaluate(devset=devset, num_threads=1, display_progress=False, display_table=5)
metric = dspy.evaluate.answer_exact_match
evaluate_on_hotpotqa(compiled_rag, metric=metric)

这些示例展示了DSPy如何简化复杂语言模型应用的开发过程,使得开发者可以更专注于系统设计而非繁琐的提示词工程。

结语

DSPy为基础模型应用开发提供了一种全新的范式,有望大幅提高开发效率和应用质量。通过上述示例,我们可以看到DSPy如何简化了复杂语言模型应用的开发过程。

reference

文档:https://dspy-docs.vercel.app/ 

论文:https://arxiv.org/abs/2310.03714

项目:https://github.com/stanfordnlp/dspy

模型篇P1:机器学习基本概念

迄今最好的AI代码编辑器,编程只需狂按Tab

【大模型实战,完整代码】AI 数据分析、可视化项目

108页PDF小册子:搭建机器学习开发环境及Python基础

116页PDF小册子:机器学习中的概率论、统计学、线性代数

全网最全 Python、机器学习、AI、LLM 速查表(100 余张)

Obsidian AI写作神器:一键配置DeepSeek,写作效率飙升1000%!

基于 QAnything 的知识库问答系统:技术解析与应用实践【附代码】


机器学习算法与Python实战
长期跟踪关注统计学、数据挖掘、机器学习算法、深度学习、人工智能技术与行业发展动态,分享Python、机器学习等技术文章。回复机器学习有惊喜资料。
 最新文章