013-多模型API调用

多模型 API 调用:一套代码同时调用 GPT、Claude 等大模型

💡 摘要:通过构建 MultiModelComparator 架构,抽象不同厂商 SDK 差异,实现并发调用多个大模型并对比响应内容、延迟和 Token 消耗。

引言

你在开发 AI 应用时,有没有遇到过这样的困扰:

  • 用 GPT-4o 写的提示词,换成 Claude 效果就不一样
  • 想同时测试多个模型的输出质量,但每个模型的 SDK 调用方式都不同
  • 想知道哪个模型响应更快、更省 Token,但要手动一个个测

不同厂商的大模型 API 接口各不相同,调用方式、响应格式、参数名称都不一样。如果为每个模型写一套调用代码,不仅冗余,还难以维护和对比。

本文将教你如何用统一的架构,一套代码同时调用 GPT-4o、Claude 等多个模型,并自动生成对比报告。

核心概念

统一响应数据结构

要对比多个模型,首先需要统一的数据格式。不同厂商的 API 返回的数据结构差异很大:

字段 OpenAI Anthropic
内容路径 response.choices[0].message.content response.content[0].text
输入 Token response.usage.prompt_tokens response.usage.input_tokens
输出 Token response.usage.completion_tokens response.usage.output_tokens

我们用一个 Python dataclass 来统一封装:

python 复制代码
from dataclasses import dataclass

@dataclass
class ModelResponse:
    """模型响应数据结构"""
    content: str           # 模型输出内容
    model_name: str        # 模型名称
    input_tokens: int      # 输入 token 数
    output_tokens: int     # 输出 token 数
    latency_ms: float      # 响应延迟(毫秒)

💡 为什么用 dataclass?

自动提供 __init____repr__ 等方法,减少样板代码。比手写类简洁得多。

SDK 差异适配

不同厂商的 SDK 调用方式差异很大:

OpenAI GPT-4o:

python 复制代码
client = AsyncOpenAI(api_key=api_key)
response = await client.chat.completions.create(
    model="gpt-4o",
    messages=[{"role": "user", "content": prompt}],
    temperature=0.7
)

Anthropic Claude:

python 复制代码
client = AsyncAnthropic(api_key=api_key)
response = await client.messages.create(
    model="claude-3-5-sonnet-latest",
    messages=[{"role": "user", "content": prompt}],
    max_tokens=2048,
    temperature=0.7
)

关键差异

  • OpenAI 用 chat.completions.create(),Claude 用 messages.create()
  • Claude 必须指定 max_tokens,OpenAI 可选
  • 响应内容的提取路径完全不同

异步并发调用

如果要同时调用多个模型,串行调用 意味着总时间 = 各模型延迟之和。使用异步并发可以让多个 API 调用同时发起,总时间 ≈ 最慢模型的延迟。

python 复制代码
import asyncio

async def compare_responses(self, prompt: str) -> Dict[str, ModelResponse]:
    """同时调用多个模型并返回对比结果"""
    tasks = [
        self.query_gpt4o(prompt),
        self.query_claude(prompt)
    ]
    results = await asyncio.gather(*tasks)
    return {r.model_name: r for r in results}

💡 asyncio.gather():同时启动多个异步任务,等待全部完成后统一返回结果。比串行快得多。

原理深入

MultiModelComparator 架构设计

整个对比框架采用工厂模式,每个模型对应一个独立的方法:

复制代码
MultiModelComparator
├── query_gpt4o()     → ModelResponse
├── query_claude()    → ModelResponse
└── compare_responses() → Dict[str, ModelResponse]

设计优势

  • 扩展简单 :新增模型只需添加一个 query_xxx() 方法,在 compare_responses() 中加入对应的 task
  • 统一返回 :所有方法都返回相同的 ModelResponse 类型
  • 异常隔离:单个模型失败不影响其他模型(可配合 try/except)

延迟测量

使用 time.time() 记录每个 API 调用的实际耗时:

python 复制代码
start_time = time.time()
response = await client.chat.completions.create(...)
latency = (time.time() - start_time) * 1000  # 转换为毫秒

延迟测量包含:网络请求时间 + 模型推理时间 + 响应返回时间。

代码示例

完整实现

python 复制代码
from typing import Dict
import os
from dataclasses import dataclass
from openai import AsyncOpenAI
import time
from anthropic import AsyncAnthropic
import asyncio

@dataclass
class ModelResponse:
    """模型响应数据结构"""
    content: str
    model_name: str
    input_tokens: int
    output_tokens: int
    latency_ms: float

class MultiModelComparator:
    """多模型 API 统一调用类"""

    def __init__(self):
        # 从环境变量读取 API Key,避免硬编码
        self.api_keys = {
            'openai': os.getenv('OPENAI_API_KEY'),
            'anthropic': os.getenv('ANTHROPIC_API_KEY'),
        }

    async def query_gpt4o(self, prompt: str) -> ModelResponse:
        """调用 GPT-4o 模型"""
        start_time = time.time()
        client = AsyncOpenAI(api_key=self.api_keys['openai'])

        response = await client.chat.completions.create(
            model="gpt-4o",
            messages=[{"role": "user", "content": prompt}],
            temperature=0.7
        )

        latency = (time.time() - start_time) * 1000

        return ModelResponse(
            content=response.choices[0].message.content,
            model_name="gpt-4o",
            input_tokens=response.usage.prompt_tokens,
            output_tokens=response.usage.completion_tokens,
            latency_ms=latency
        )

    async def query_claude(self, prompt: str) -> ModelResponse:
        """调用 Claude 3.5 Sonnet"""
        start_time = time.time()
        client = AsyncAnthropic(api_key=self.api_keys['anthropic'])

        response = await client.messages.create(
            model="claude-3-5-sonnet-latest",
            messages=[{"role": "user", "content": prompt}],
            max_tokens=2048,
            temperature=0.7
        )

        latency = (time.time() - start_time) * 1000

        return ModelResponse(
            content=response.content[0].text,
            model_name="claude-3.5-sonnet",
            input_tokens=response.usage.input_tokens,
            output_tokens=response.usage.output_tokens,
            latency_ms=latency
        )

    async def compare_responses(self, prompt: str) -> Dict[str, ModelResponse]:
        """同时调用多个模型并返回对比结果"""
        tasks = [
            self.query_gpt4o(prompt),
            self.query_claude(prompt)
        ]
        results = await asyncio.gather(*tasks)
        return {r.model_name: r for r in results}

运行测试与对比报告

python 复制代码
async def main():
    comparator = MultiModelComparator()
    test_prompt = "用 Python 实现一个快速排序算法,并解释时间复杂度"

    print("正在并发调用多个模型...")
    results = await comparator.compare_responses(test_prompt)

    # 打印对比报告
    print("\n===== 模型对比报告 =====")
    for model_name, response in results.items():
        print(f"\n【{model_name}】")
        print(f"响应时间:{response.latency_ms:.0f}ms")
        print(f"输入 Token: {response.input_tokens}")
        print(f"输出 Token: {response.output_tokens}")
        print(f"内容预览:{response.content[:100]}...")

asyncio.run(main())

输出示例

复制代码
===== 模型对比报告 =====

【gpt-4o】
响应时间:1230ms
输入 Token: 45
输出 Token: 312
内容预览:def quick_sort(arr):
    if len(arr) <= 1:
        return arr
    ...

【claude-3.5-sonnet】
响应时间:980ms
输入 Token: 38
输出 Token: 285
内容预览:快速排序(Quicksort)是一种基于分治思想的高效排序算法...

实战应用

如何扩展更多模型?

只需添加新的查询方法,并在 compare_responses() 中注册:

python 复制代码
async def query_gemini(self, prompt: str) -> ModelResponse:
    """调用 Google Gemini"""
    start_time = time.time()
    # Gemini SDK 调用代码...
    latency = (time.time() - start_time) * 1000
    return ModelResponse(...)

# 在 compare_responses 中添加
tasks = [
    self.query_gpt4o(prompt),
    self.query_claude(prompt),
    self.query_gemini(prompt)  # 新增
]

添加异常处理

单个模型失败不应影响其他模型:

python 复制代码
async def query_gpt4o(self, prompt: str) -> ModelResponse:
    try:
        # ... 调用代码
        return ModelResponse(...)
    except Exception as e:
        return ModelResponse(
            content=f"调用失败:{str(e)}",
            model_name="gpt-4o",
            input_tokens=0,
            output_tokens=0,
            latency_ms=-1
        )

最佳实践

  1. API Key 从环境变量读取 :使用 os.getenv() 避免硬编码敏感信息
  2. 统一响应格式 :所有模型返回相同的 ModelResponse 结构,便于后续处理
  3. 异步并发 :使用 asyncio.gather() 减少总等待时间
  4. 异常隔离:单个模型失败不应影响其他模型的调用
  5. 延迟测量:包含网络请求 + 推理 + 响应的完整时间
  6. 温度统一 :对比时保持 temperature 一致,否则输出风格差异会干扰判断

总结

多模型 API 调用的核心要点:

  • 统一数据结构 :用 ModelResponse dataclass 封装不同模型的响应
  • SDK 适配:OpenAI 和 Anthropic 的调用方式不同,需分别适配
  • 异步并发asyncio.gather() 让多个 API 调用同时进行
  • 对比报告:统一格式后,轻松对比响应内容、延迟和 Token 消耗
  • 扩展简单:新增模型只需添加一个查询方法

掌握了多模型 API 调用,就能高效对比不同模型的性能和输出质量,为应用选择最合适的模型。


相关推荐
guslegend4 小时前
第10节:后端业务基础设施
大模型
汤姆yu8 小时前
视觉编程革命:智谱GLM-5V-Turbo引领Design2Code新范式
ai·大模型·视觉革命
belldeep9 小时前
CSR座席模块 如何结合AI 大模型应用?
人工智能·ai·大模型·csr坐席
小何code9 小时前
人工智能【第30篇】AI学习路径总结与职业规划指南
人工智能·大模型·职业规划·ai学习路径
li星野12 小时前
LlamaIndex 核心模块详解:从数据连接到智能代理,构建生产级 RAG 系统
大模型·llamaindex·学习记录
Wilber的技术分享12 小时前
【大模型面试八股 2】Function Call、MCP、Skill的区别
人工智能·面试·职场和发展·大模型·llm·agent·智能体开发
Bruce_Liuxiaowei13 小时前
WorkBuddy案例——教育辅导智能体
人工智能·ai·大模型·智能体·龙虾·workbuddy
熊猫钓鱼>_>13 小时前
Q-Learning详解:从理论到实战的完整指南
人工智能·python·架构·大模型·llm·machine learning·q-learning
guslegend15 小时前
第4节:UI页面对接(流式应答界面)
人工智能·大模型