LangChain Model I/O:模型调用完全指南

文章目录

  • [一、什么是 Model I/O](#一、什么是 Model I/O)
  • 二、三种模型类型,别搞混了
  • 三、统一接口:写一遍,哪都能跑
  • [四、ChatOpenAI 核心参数](#四、ChatOpenAI 核心参数)
    • [temperature 怎么选?](#temperature 怎么选?)
    • [Token 到底是什么?](#Token 到底是什么?)
  • [五、四种消息类型 & 三种传入方式](#五、四种消息类型 & 三种传入方式)
  • [六、四种调用方式:invoke / ainvoke / stream / batch](#六、四种调用方式:invoke / ainvoke / stream / batch)
    • [6.1 invoke() --- 同步调用](#6.1 invoke() — 同步调用)
    • [6.2 ainvoke() --- 异步调用](#6.2 ainvoke() — 异步调用)
    • [6.3 stream() --- 流式输出](#6.3 stream() — 流式输出)
    • [6.4 batch() --- 批量调用](#6.4 batch() — 批量调用)
  • 七、多平台接入实战
    • [7.1 兼容 OpenAI 格式的平台](#7.1 兼容 OpenAI 格式的平台)
    • [7.2 不兼容 OpenAI 格式的平台](#7.2 不兼容 OpenAI 格式的平台)
    • [7.3 各平台速查表](#7.3 各平台速查表)
  • 八、本地模型:Ollama
  • 九、几个值得了解的高级特性
    • [9.1 多模态输入](#9.1 多模态输入)
    • [9.2 速率限制](#9.2 速率限制)
    • [9.3 Token 用量追踪](#9.3 Token 用量追踪)
    • [9.4 提示词缓存](#9.4 提示词缓存)
    • [9.5 运行时动态切换模型](#9.5 运行时动态切换模型)
  • 十、小结

一、什么是 Model I/O

Model I/O 是 LangChain 与大语言模型交互的核心流程。它回答一个最基本的问题:怎么把问题喂给模型,并拿到有用的结果?

整个流程拆成三个环节:
#mermaid-svg-00rQaurS9xBCs7Xk{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}@keyframes edge-animation-frame{from{stroke-dashoffset:0;}}@keyframes dash{to{stroke-dashoffset:0;}}#mermaid-svg-00rQaurS9xBCs7Xk .edge-animation-slow{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 50s linear infinite;stroke-linecap:round;}#mermaid-svg-00rQaurS9xBCs7Xk .edge-animation-fast{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 20s linear infinite;stroke-linecap:round;}#mermaid-svg-00rQaurS9xBCs7Xk .error-icon{fill:#552222;}#mermaid-svg-00rQaurS9xBCs7Xk .error-text{fill:#552222;stroke:#552222;}#mermaid-svg-00rQaurS9xBCs7Xk .edge-thickness-normal{stroke-width:1px;}#mermaid-svg-00rQaurS9xBCs7Xk .edge-thickness-thick{stroke-width:3.5px;}#mermaid-svg-00rQaurS9xBCs7Xk .edge-pattern-solid{stroke-dasharray:0;}#mermaid-svg-00rQaurS9xBCs7Xk .edge-thickness-invisible{stroke-width:0;fill:none;}#mermaid-svg-00rQaurS9xBCs7Xk .edge-pattern-dashed{stroke-dasharray:3;}#mermaid-svg-00rQaurS9xBCs7Xk .edge-pattern-dotted{stroke-dasharray:2;}#mermaid-svg-00rQaurS9xBCs7Xk .marker{fill:#333333;stroke:#333333;}#mermaid-svg-00rQaurS9xBCs7Xk .marker.cross{stroke:#333333;}#mermaid-svg-00rQaurS9xBCs7Xk svg{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;}#mermaid-svg-00rQaurS9xBCs7Xk p{margin:0;}#mermaid-svg-00rQaurS9xBCs7Xk .label{font-family:"trebuchet ms",verdana,arial,sans-serif;color:#333;}#mermaid-svg-00rQaurS9xBCs7Xk .cluster-label text{fill:#333;}#mermaid-svg-00rQaurS9xBCs7Xk .cluster-label span{color:#333;}#mermaid-svg-00rQaurS9xBCs7Xk .cluster-label span p{background-color:transparent;}#mermaid-svg-00rQaurS9xBCs7Xk .label text,#mermaid-svg-00rQaurS9xBCs7Xk span{fill:#333;color:#333;}#mermaid-svg-00rQaurS9xBCs7Xk .node rect,#mermaid-svg-00rQaurS9xBCs7Xk .node circle,#mermaid-svg-00rQaurS9xBCs7Xk .node ellipse,#mermaid-svg-00rQaurS9xBCs7Xk .node polygon,#mermaid-svg-00rQaurS9xBCs7Xk .node path{fill:#ECECFF;stroke:#9370DB;stroke-width:1px;}#mermaid-svg-00rQaurS9xBCs7Xk .rough-node .label text,#mermaid-svg-00rQaurS9xBCs7Xk .node .label text,#mermaid-svg-00rQaurS9xBCs7Xk .image-shape .label,#mermaid-svg-00rQaurS9xBCs7Xk .icon-shape .label{text-anchor:middle;}#mermaid-svg-00rQaurS9xBCs7Xk .node .katex path{fill:#000;stroke:#000;stroke-width:1px;}#mermaid-svg-00rQaurS9xBCs7Xk .rough-node .label,#mermaid-svg-00rQaurS9xBCs7Xk .node .label,#mermaid-svg-00rQaurS9xBCs7Xk .image-shape .label,#mermaid-svg-00rQaurS9xBCs7Xk .icon-shape .label{text-align:center;}#mermaid-svg-00rQaurS9xBCs7Xk .node.clickable{cursor:pointer;}#mermaid-svg-00rQaurS9xBCs7Xk .root .anchor path{fill:#333333!important;stroke-width:0;stroke:#333333;}#mermaid-svg-00rQaurS9xBCs7Xk .arrowheadPath{fill:#333333;}#mermaid-svg-00rQaurS9xBCs7Xk .edgePath .path{stroke:#333333;stroke-width:2.0px;}#mermaid-svg-00rQaurS9xBCs7Xk .flowchart-link{stroke:#333333;fill:none;}#mermaid-svg-00rQaurS9xBCs7Xk .edgeLabel{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-00rQaurS9xBCs7Xk .edgeLabel p{background-color:rgba(232,232,232, 0.8);}#mermaid-svg-00rQaurS9xBCs7Xk .edgeLabel rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-00rQaurS9xBCs7Xk .labelBkg{background-color:rgba(232, 232, 232, 0.5);}#mermaid-svg-00rQaurS9xBCs7Xk .cluster rect{fill:#ffffde;stroke:#aaaa33;stroke-width:1px;}#mermaid-svg-00rQaurS9xBCs7Xk .cluster text{fill:#333;}#mermaid-svg-00rQaurS9xBCs7Xk .cluster span{color:#333;}#mermaid-svg-00rQaurS9xBCs7Xk div.mermaidTooltip{position:absolute;text-align:center;max-width:200px;padding:2px;font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:12px;background:hsl(80, 100%, 96.2745098039%);border:1px solid #aaaa33;border-radius:2px;pointer-events:none;z-index:100;}#mermaid-svg-00rQaurS9xBCs7Xk .flowchartTitleText{text-anchor:middle;font-size:18px;fill:#333;}#mermaid-svg-00rQaurS9xBCs7Xk rect.text{fill:none;stroke-width:0;}#mermaid-svg-00rQaurS9xBCs7Xk .icon-shape,#mermaid-svg-00rQaurS9xBCs7Xk .image-shape{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-00rQaurS9xBCs7Xk .icon-shape p,#mermaid-svg-00rQaurS9xBCs7Xk .image-shape p{background-color:rgba(232,232,232, 0.8);padding:2px;}#mermaid-svg-00rQaurS9xBCs7Xk .icon-shape .label rect,#mermaid-svg-00rQaurS9xBCs7Xk .image-shape .label rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-00rQaurS9xBCs7Xk .label-icon{display:inline-block;height:1em;overflow:visible;vertical-align:-0.125em;}#mermaid-svg-00rQaurS9xBCs7Xk .node .label-icon path{fill:currentColor;stroke:revert;stroke-width:revert;}#mermaid-svg-00rQaurS9xBCs7Xk :root{--mermaid-font-family:"trebuchet ms",verdana,arial,sans-serif;} 格式化消息
统一接口调用
文本→JSON/Pydantic
你的问题
Prompts

提示词模板
Models

模型调用
Output Parsers

输出解析
结构化结果

  • Prompts:把用户输入和系统指令格式化成模型能理解的消息
  • Models:统一接口调用不同平台的模型(OpenAI、DeepSeek、本地模型等)
  • Output Parsers:把模型返回的文本转换为 JSON、Pydantic 对象等结构化数据

本文聚焦中间环节------Models(模型调用)。

二、三种模型类型,别搞混了

LangChain 把模型分成了三类,命名很容易让人糊涂,先理清楚:

类型 输入 → 输出 代表类 现状
Chat Models(对话型) 消息列表 → AI 消息 ChatOpenAIChatAnthropicChatOllama 当前主流,GPT-4o、Claude、DeepSeek 都走这个
LLMs(补全型) 字符串 → 字符串 OpenAI(旧版) 基本淘汰,GPT-3 时代的 text-davinci 遗留产物
Embeddings(向量型) 文本 → 浮点数向量 OpenAIEmbeddings 不生成文本,专用于语义搜索和 RAG

结论:除非特别说明,"模型调用"都是指 Chat Models。LLMs 这个遗留接口可以无视。

Chat Models 的核心设计理念是:输入是一组消息(有角色、有上下文),输出也是一个有角色标注的消息对象。这和直接 requests.post 拿回一段裸文本有本质区别------消息对象携带了角色信息、token 用量、模型名称等元数据,后续链路里的 Agent、Memory、Tools 都会用到这些信息。

三、统一接口:写一遍,哪都能跑

LangChain 的 Models 层最大的价值不是"帮你调 API",而是"让你不用关心调的是谁的 API"。

python 复制代码
# 不同平台,同一个调用姿势
llm = ChatOpenAI(model="gpt-4o-mini")                          # OpenAI
llm = ChatOpenAI(model="deepseek-chat", ...)                   # DeepSeek
llm = ChatAnthropic(model="claude-sonnet-4-20250514")          # Anthropic
llm = ChatOllama(model="qwen2.5:7b")                           # 本地模型

# 以下调用方式全部通用
response = llm.invoke("你好")              # 同步调用
response = await llm.ainvoke("你好")        # 异步调用
for chunk in llm.stream("你好"):           # 流式输出
    print(chunk.content, end="")
responses = llm.batch(["问题1", "问题2"])   # 批量调用

原生 SDK 的世界里,从 OpenAI 换到 Anthropic 意味着从 client.chat.completions.create() 变成 client.messages.create(),取结果从 .choices[0].message.content 变成 .content[0].text。每换一个平台,重写一遍取值逻辑。LangChain 把这些差异全部封装了进去,你只需要换一行初始化。
#mermaid-svg-5CnECrMEt8NrG6qo{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}@keyframes edge-animation-frame{from{stroke-dashoffset:0;}}@keyframes dash{to{stroke-dashoffset:0;}}#mermaid-svg-5CnECrMEt8NrG6qo .edge-animation-slow{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 50s linear infinite;stroke-linecap:round;}#mermaid-svg-5CnECrMEt8NrG6qo .edge-animation-fast{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 20s linear infinite;stroke-linecap:round;}#mermaid-svg-5CnECrMEt8NrG6qo .error-icon{fill:#552222;}#mermaid-svg-5CnECrMEt8NrG6qo .error-text{fill:#552222;stroke:#552222;}#mermaid-svg-5CnECrMEt8NrG6qo .edge-thickness-normal{stroke-width:1px;}#mermaid-svg-5CnECrMEt8NrG6qo .edge-thickness-thick{stroke-width:3.5px;}#mermaid-svg-5CnECrMEt8NrG6qo .edge-pattern-solid{stroke-dasharray:0;}#mermaid-svg-5CnECrMEt8NrG6qo .edge-thickness-invisible{stroke-width:0;fill:none;}#mermaid-svg-5CnECrMEt8NrG6qo .edge-pattern-dashed{stroke-dasharray:3;}#mermaid-svg-5CnECrMEt8NrG6qo .edge-pattern-dotted{stroke-dasharray:2;}#mermaid-svg-5CnECrMEt8NrG6qo .marker{fill:#333333;stroke:#333333;}#mermaid-svg-5CnECrMEt8NrG6qo .marker.cross{stroke:#333333;}#mermaid-svg-5CnECrMEt8NrG6qo svg{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;}#mermaid-svg-5CnECrMEt8NrG6qo p{margin:0;}#mermaid-svg-5CnECrMEt8NrG6qo .label{font-family:"trebuchet ms",verdana,arial,sans-serif;color:#333;}#mermaid-svg-5CnECrMEt8NrG6qo .cluster-label text{fill:#333;}#mermaid-svg-5CnECrMEt8NrG6qo .cluster-label span{color:#333;}#mermaid-svg-5CnECrMEt8NrG6qo .cluster-label span p{background-color:transparent;}#mermaid-svg-5CnECrMEt8NrG6qo .label text,#mermaid-svg-5CnECrMEt8NrG6qo span{fill:#333;color:#333;}#mermaid-svg-5CnECrMEt8NrG6qo .node rect,#mermaid-svg-5CnECrMEt8NrG6qo .node circle,#mermaid-svg-5CnECrMEt8NrG6qo .node ellipse,#mermaid-svg-5CnECrMEt8NrG6qo .node polygon,#mermaid-svg-5CnECrMEt8NrG6qo .node path{fill:#ECECFF;stroke:#9370DB;stroke-width:1px;}#mermaid-svg-5CnECrMEt8NrG6qo .rough-node .label text,#mermaid-svg-5CnECrMEt8NrG6qo .node .label text,#mermaid-svg-5CnECrMEt8NrG6qo .image-shape .label,#mermaid-svg-5CnECrMEt8NrG6qo .icon-shape .label{text-anchor:middle;}#mermaid-svg-5CnECrMEt8NrG6qo .node .katex path{fill:#000;stroke:#000;stroke-width:1px;}#mermaid-svg-5CnECrMEt8NrG6qo .rough-node .label,#mermaid-svg-5CnECrMEt8NrG6qo .node .label,#mermaid-svg-5CnECrMEt8NrG6qo .image-shape .label,#mermaid-svg-5CnECrMEt8NrG6qo .icon-shape .label{text-align:center;}#mermaid-svg-5CnECrMEt8NrG6qo .node.clickable{cursor:pointer;}#mermaid-svg-5CnECrMEt8NrG6qo .root .anchor path{fill:#333333!important;stroke-width:0;stroke:#333333;}#mermaid-svg-5CnECrMEt8NrG6qo .arrowheadPath{fill:#333333;}#mermaid-svg-5CnECrMEt8NrG6qo .edgePath .path{stroke:#333333;stroke-width:2.0px;}#mermaid-svg-5CnECrMEt8NrG6qo .flowchart-link{stroke:#333333;fill:none;}#mermaid-svg-5CnECrMEt8NrG6qo .edgeLabel{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-5CnECrMEt8NrG6qo .edgeLabel p{background-color:rgba(232,232,232, 0.8);}#mermaid-svg-5CnECrMEt8NrG6qo .edgeLabel rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-5CnECrMEt8NrG6qo .labelBkg{background-color:rgba(232, 232, 232, 0.5);}#mermaid-svg-5CnECrMEt8NrG6qo .cluster rect{fill:#ffffde;stroke:#aaaa33;stroke-width:1px;}#mermaid-svg-5CnECrMEt8NrG6qo .cluster text{fill:#333;}#mermaid-svg-5CnECrMEt8NrG6qo .cluster span{color:#333;}#mermaid-svg-5CnECrMEt8NrG6qo div.mermaidTooltip{position:absolute;text-align:center;max-width:200px;padding:2px;font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:12px;background:hsl(80, 100%, 96.2745098039%);border:1px solid #aaaa33;border-radius:2px;pointer-events:none;z-index:100;}#mermaid-svg-5CnECrMEt8NrG6qo .flowchartTitleText{text-anchor:middle;font-size:18px;fill:#333;}#mermaid-svg-5CnECrMEt8NrG6qo rect.text{fill:none;stroke-width:0;}#mermaid-svg-5CnECrMEt8NrG6qo .icon-shape,#mermaid-svg-5CnECrMEt8NrG6qo .image-shape{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-5CnECrMEt8NrG6qo .icon-shape p,#mermaid-svg-5CnECrMEt8NrG6qo .image-shape p{background-color:rgba(232,232,232, 0.8);padding:2px;}#mermaid-svg-5CnECrMEt8NrG6qo .icon-shape .label rect,#mermaid-svg-5CnECrMEt8NrG6qo .image-shape .label rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-5CnECrMEt8NrG6qo .label-icon{display:inline-block;height:1em;overflow:visible;vertical-align:-0.125em;}#mermaid-svg-5CnECrMEt8NrG6qo .node .label-icon path{fill:currentColor;stroke:revert;stroke-width:revert;}#mermaid-svg-5CnECrMEt8NrG6qo :root{--mermaid-font-family:"trebuchet ms",verdana,arial,sans-serif;} 切换成本:高
LangChain:只改一行初始化
统一 .invoke() → .content
统一 .invoke() → .content
ChatOpenAI(model='gpt-4o-mini')
ChatAnthropic(model='claude-...')
ChatOpenAI(model='deepseek-chat', base_url=...)
原生 SDK:每换一次平台,改一堆代码
OpenAI SDK

client.chat.completions.create()

取 .choices0.message.content
Anthropic SDK

client.messages.create()

取 .content0.text

(参数、返回格式完全不同)
DeepSeek SDK

兼容 OpenAI 但参数不同

四、ChatOpenAI 核心参数

日常开发大多场景用的都是 ChatOpenAI,初始化参数不多,但每个都有实际影响:

python 复制代码
llm = ChatOpenAI(
    model="gpt-4o-mini",    # 模型名称,必填
    temperature=0.7,        # 随机性,决定"创造力"
    max_tokens=1000,        # 最大输出长度
    timeout=60,             # 超时秒数
    max_retries=2,          # 失败重试次数
)

temperature 怎么选?

temperature 直接控制输出的"确定性"和"创造性",不同场景有比较明确的取值区间:

场景 推荐 temperature 原因
代码生成、数据提取、翻译 0 ~ 0.3 需要稳定、准确
问答、摘要、分析 0.3 ~ 0.7 兼顾准确和流畅
创意写作、头脑风暴 0.7 ~ 1.0 需要多样性

temperature=0 时每次调用结果几乎一致,temperature=1 时每次都可能不同。别被名字误导,它不等于"温度",本质上是一个控制概率分布的参数。

补充说明

针对于temperature取值范围存在以下说明

不同厂商的 API 存在细微差异:例如 OpenAI GPT 系列官方取值范围为 0~2;部分国内大模型、轻量化推理框架会将上限设为 1,超出范围的取值可能被自动截断。

Token 到底是什么?

Token 不是字数,不是单词数,是大模型处理文本的最小单位。同一个"你好世界",中文模型可能切成 2 个 token,英文模型可能切成 3 个 token,完全取决于分词器。

语言 1 个 Token 大约等于
中文 1 ~ 1.8 个汉字
英文 3 ~ 4 个字母

不同模型的分词器不一样。OpenAI 的 GPT-4o 用 o200k_base,Claude 有自己的分词器,两者切同一段文本的 token 数可能差 10%~20%。所以"1000 token 能出多少字"这个问题没法给统一答案,得看具体模型。

调用成本不是只看回答长短,输入 token 也计费。喂给模型的上下文越长,单次调用越贵。

max_tokens 限制的是输出最大 token 数,如果发现回答被截断,多半是它设小了。

五、四种消息类型 & 三种传入方式

消息类型

模型不接收纯字符串,而是接收有角色标注的消息列表。四个角色各有分工:

消息类型 类名 干什么
系统消息 SystemMessage 设定 AI 的人设、行为规则
用户消息 HumanMessage 用户的问题或指令
AI 消息 AIMessage AI 的回复,用于填充对话历史
工具消息 ToolMessage 工具调用返回的结果

记忆口诀:系统定规则,用户提问题,AI 给回复,工具报结果。

python 复制代码
from langchain_core.messages import HumanMessage, SystemMessage, AIMessage

conversation = [
    SystemMessage(content="你是一个专业的 Python 编程助手"),
    HumanMessage(content="什么是装饰器?"),
    AIMessage(content="装饰器是用于修改函数行为的..."),
    HumanMessage(content="举一个实际例子"),
]
response = llm.invoke(conversation)

传入方式:三种写法怎么选

#mermaid-svg-CXzgYS4TtPSjBFAk{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}@keyframes edge-animation-frame{from{stroke-dashoffset:0;}}@keyframes dash{to{stroke-dashoffset:0;}}#mermaid-svg-CXzgYS4TtPSjBFAk .edge-animation-slow{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 50s linear infinite;stroke-linecap:round;}#mermaid-svg-CXzgYS4TtPSjBFAk .edge-animation-fast{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 20s linear infinite;stroke-linecap:round;}#mermaid-svg-CXzgYS4TtPSjBFAk .error-icon{fill:#552222;}#mermaid-svg-CXzgYS4TtPSjBFAk .error-text{fill:#552222;stroke:#552222;}#mermaid-svg-CXzgYS4TtPSjBFAk .edge-thickness-normal{stroke-width:1px;}#mermaid-svg-CXzgYS4TtPSjBFAk .edge-thickness-thick{stroke-width:3.5px;}#mermaid-svg-CXzgYS4TtPSjBFAk .edge-pattern-solid{stroke-dasharray:0;}#mermaid-svg-CXzgYS4TtPSjBFAk .edge-thickness-invisible{stroke-width:0;fill:none;}#mermaid-svg-CXzgYS4TtPSjBFAk .edge-pattern-dashed{stroke-dasharray:3;}#mermaid-svg-CXzgYS4TtPSjBFAk .edge-pattern-dotted{stroke-dasharray:2;}#mermaid-svg-CXzgYS4TtPSjBFAk .marker{fill:#333333;stroke:#333333;}#mermaid-svg-CXzgYS4TtPSjBFAk .marker.cross{stroke:#333333;}#mermaid-svg-CXzgYS4TtPSjBFAk svg{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;}#mermaid-svg-CXzgYS4TtPSjBFAk p{margin:0;}#mermaid-svg-CXzgYS4TtPSjBFAk .label{font-family:"trebuchet ms",verdana,arial,sans-serif;color:#333;}#mermaid-svg-CXzgYS4TtPSjBFAk .cluster-label text{fill:#333;}#mermaid-svg-CXzgYS4TtPSjBFAk .cluster-label span{color:#333;}#mermaid-svg-CXzgYS4TtPSjBFAk .cluster-label span p{background-color:transparent;}#mermaid-svg-CXzgYS4TtPSjBFAk .label text,#mermaid-svg-CXzgYS4TtPSjBFAk span{fill:#333;color:#333;}#mermaid-svg-CXzgYS4TtPSjBFAk .node rect,#mermaid-svg-CXzgYS4TtPSjBFAk .node circle,#mermaid-svg-CXzgYS4TtPSjBFAk .node ellipse,#mermaid-svg-CXzgYS4TtPSjBFAk .node polygon,#mermaid-svg-CXzgYS4TtPSjBFAk .node path{fill:#ECECFF;stroke:#9370DB;stroke-width:1px;}#mermaid-svg-CXzgYS4TtPSjBFAk .rough-node .label text,#mermaid-svg-CXzgYS4TtPSjBFAk .node .label text,#mermaid-svg-CXzgYS4TtPSjBFAk .image-shape .label,#mermaid-svg-CXzgYS4TtPSjBFAk .icon-shape .label{text-anchor:middle;}#mermaid-svg-CXzgYS4TtPSjBFAk .node .katex path{fill:#000;stroke:#000;stroke-width:1px;}#mermaid-svg-CXzgYS4TtPSjBFAk .rough-node .label,#mermaid-svg-CXzgYS4TtPSjBFAk .node .label,#mermaid-svg-CXzgYS4TtPSjBFAk .image-shape .label,#mermaid-svg-CXzgYS4TtPSjBFAk .icon-shape .label{text-align:center;}#mermaid-svg-CXzgYS4TtPSjBFAk .node.clickable{cursor:pointer;}#mermaid-svg-CXzgYS4TtPSjBFAk .root .anchor path{fill:#333333!important;stroke-width:0;stroke:#333333;}#mermaid-svg-CXzgYS4TtPSjBFAk .arrowheadPath{fill:#333333;}#mermaid-svg-CXzgYS4TtPSjBFAk .edgePath .path{stroke:#333333;stroke-width:2.0px;}#mermaid-svg-CXzgYS4TtPSjBFAk .flowchart-link{stroke:#333333;fill:none;}#mermaid-svg-CXzgYS4TtPSjBFAk .edgeLabel{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-CXzgYS4TtPSjBFAk .edgeLabel p{background-color:rgba(232,232,232, 0.8);}#mermaid-svg-CXzgYS4TtPSjBFAk .edgeLabel rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-CXzgYS4TtPSjBFAk .labelBkg{background-color:rgba(232, 232, 232, 0.5);}#mermaid-svg-CXzgYS4TtPSjBFAk .cluster rect{fill:#ffffde;stroke:#aaaa33;stroke-width:1px;}#mermaid-svg-CXzgYS4TtPSjBFAk .cluster text{fill:#333;}#mermaid-svg-CXzgYS4TtPSjBFAk .cluster span{color:#333;}#mermaid-svg-CXzgYS4TtPSjBFAk div.mermaidTooltip{position:absolute;text-align:center;max-width:200px;padding:2px;font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:12px;background:hsl(80, 100%, 96.2745098039%);border:1px solid #aaaa33;border-radius:2px;pointer-events:none;z-index:100;}#mermaid-svg-CXzgYS4TtPSjBFAk .flowchartTitleText{text-anchor:middle;font-size:18px;fill:#333;}#mermaid-svg-CXzgYS4TtPSjBFAk rect.text{fill:none;stroke-width:0;}#mermaid-svg-CXzgYS4TtPSjBFAk .icon-shape,#mermaid-svg-CXzgYS4TtPSjBFAk .image-shape{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-CXzgYS4TtPSjBFAk .icon-shape p,#mermaid-svg-CXzgYS4TtPSjBFAk .image-shape p{background-color:rgba(232,232,232, 0.8);padding:2px;}#mermaid-svg-CXzgYS4TtPSjBFAk .icon-shape .label rect,#mermaid-svg-CXzgYS4TtPSjBFAk .image-shape .label rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-CXzgYS4TtPSjBFAk .label-icon{display:inline-block;height:1em;overflow:visible;vertical-align:-0.125em;}#mermaid-svg-CXzgYS4TtPSjBFAk .node .label-icon path{fill:currentColor;stroke:revert;stroke-width:revert;}#mermaid-svg-CXzgYS4TtPSjBFAk :root{--mermaid-font-family:"trebuchet ms",verdana,arial,sans-serif;} 不需要
需要


我要调用模型
需要角色设定

或对话历史吗?
方式一:直接传字符串

llm.invoke('你好')
消息是动态构建的吗?

比如从模板/配置读取
方式三:元组或字典

('system', '...'), ('user', '...')

方式二:消息列表

SystemMessage(...), HumanMessage(...)

方式 代码 适用场景
直接字符串 llm.invoke("你好") 简单问答,不需要上下文
消息列表 llm.invoke([SystemMessage(...), HumanMessage(...)]) 需角色设定或对话历史,最常用
元组/字典 llm.invoke([("system", "..."), ("user", "...")]) 动态构建消息,从配置读取模板

用消息列表的好处不只是能设角色------当你需要保留对话上下文时,把历史 AIMessage 继续拼在列表尾部就行,模型就能"记得"刚才聊过什么。

六、四种调用方式:invoke / ainvoke / stream / batch

这是日常开发里用得最多的四个方法,各自有明确的适用场景。

6.1 invoke() --- 同步调用

最基础的方式,调一次、等结果、拿内容:

python 复制代码
response = llm.invoke("什么是 LangChain?")
print(response.content)  # 注意:返回的是 AIMessage 对象,不是字符串

适合脚本、Jupyter 原型开发、不需要并发的场景。

6.2 ainvoke() --- 异步调用

invoke 加上 a 前缀,搭配 asyncio.gather 能把多个请求的等待时间重叠起来。先建立一个直觉:

  • 同步 invoke = 在奶茶店排队:你点一杯,等 10 分钟做好,再点下一杯,再等 10 分钟。5 杯 = 50 分钟
  • 异步 ainvoke + gather = 扫码同时下 5 单:哪杯好了取哪杯,5 杯 ≈ 10 分钟

API 服务 主线程 API 服务 主线程 #mermaid-svg-zHkA3Q8KFI8n0l8Z{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}@keyframes edge-animation-frame{from{stroke-dashoffset:0;}}@keyframes dash{to{stroke-dashoffset:0;}}#mermaid-svg-zHkA3Q8KFI8n0l8Z .edge-animation-slow{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 50s linear infinite;stroke-linecap:round;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .edge-animation-fast{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 20s linear infinite;stroke-linecap:round;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .error-icon{fill:#552222;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .error-text{fill:#552222;stroke:#552222;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .edge-thickness-normal{stroke-width:1px;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .edge-thickness-thick{stroke-width:3.5px;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .edge-pattern-solid{stroke-dasharray:0;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .edge-thickness-invisible{stroke-width:0;fill:none;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .edge-pattern-dashed{stroke-dasharray:3;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .edge-pattern-dotted{stroke-dasharray:2;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .marker{fill:#333333;stroke:#333333;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .marker.cross{stroke:#333333;}#mermaid-svg-zHkA3Q8KFI8n0l8Z svg{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;}#mermaid-svg-zHkA3Q8KFI8n0l8Z p{margin:0;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .actor{stroke:hsl(259.6261682243, 59.7765363128%, 87.9019607843%);fill:#ECECFF;}#mermaid-svg-zHkA3Q8KFI8n0l8Z text.actor>tspan{fill:black;stroke:none;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .actor-line{stroke:hsl(259.6261682243, 59.7765363128%, 87.9019607843%);}#mermaid-svg-zHkA3Q8KFI8n0l8Z .innerArc{stroke-width:1.5;stroke-dasharray:none;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .messageLine0{stroke-width:1.5;stroke-dasharray:none;stroke:#333;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .messageLine1{stroke-width:1.5;stroke-dasharray:2,2;stroke:#333;}#mermaid-svg-zHkA3Q8KFI8n0l8Z #arrowhead path{fill:#333;stroke:#333;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .sequenceNumber{fill:white;}#mermaid-svg-zHkA3Q8KFI8n0l8Z #sequencenumber{fill:#333;}#mermaid-svg-zHkA3Q8KFI8n0l8Z #crosshead path{fill:#333;stroke:#333;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .messageText{fill:#333;stroke:none;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .labelBox{stroke:hsl(259.6261682243, 59.7765363128%, 87.9019607843%);fill:#ECECFF;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .labelText,#mermaid-svg-zHkA3Q8KFI8n0l8Z .labelText>tspan{fill:black;stroke:none;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .loopText,#mermaid-svg-zHkA3Q8KFI8n0l8Z .loopText>tspan{fill:black;stroke:none;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .loopLine{stroke-width:2px;stroke-dasharray:2,2;stroke:hsl(259.6261682243, 59.7765363128%, 87.9019607843%);fill:hsl(259.6261682243, 59.7765363128%, 87.9019607843%);}#mermaid-svg-zHkA3Q8KFI8n0l8Z .note{stroke:#aaaa33;fill:#fff5ad;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .noteText,#mermaid-svg-zHkA3Q8KFI8n0l8Z .noteText>tspan{fill:black;stroke:none;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .activation0{fill:#f4f4f4;stroke:#666;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .activation1{fill:#f4f4f4;stroke:#666;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .activation2{fill:#f4f4f4;stroke:#666;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .actorPopupMenu{position:absolute;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .actorPopupMenuPanel{position:absolute;fill:#ECECFF;box-shadow:0px 8px 16px 0px rgba(0,0,0,0.2);filter:drop-shadow(3px 5px 2px rgb(0 0 0 / 0.4));}#mermaid-svg-zHkA3Q8KFI8n0l8Z .actor-man line{stroke:hsl(259.6261682243, 59.7765363128%, 87.9019607843%);fill:#ECECFF;}#mermaid-svg-zHkA3Q8KFI8n0l8Z .actor-man circle,#mermaid-svg-zHkA3Q8KFI8n0l8Z line{stroke:hsl(259.6261682243, 59.7765363128%, 87.9019607843%);fill:#ECECFF;stroke-width:2px;}#mermaid-svg-zHkA3Q8KFI8n0l8Z :root{--mermaid-font-family:"trebuchet ms",verdana,arial,sans-serif;} 同步 invoke(串行) 异步 ainvoke + gather(并行) 请求 1 响应 1(等了 2s) 请求 2 响应 2(等了 2s) 请求 3 响应 3(等了 2s) 请求 1、2、3 同时发出 三个响应几乎同时返回(≈2s)

关键代码:

python 复制代码
import asyncio

async def parallel_calls():
    tasks = [
        llm.ainvoke("问题1"),
        llm.ainvoke("问题2"),
        llm.ainvoke("问题3"),
    ]
    results = await asyncio.gather(*tasks)
    # 三个请求同时发出,总耗时 ≈ 最慢的那个

一个容易踩的坑:用 await llm.ainvoke() 一个一个调还是串行的,只有配合 asyncio.gather 才有并行效果。ainvoke 负责"能让出 CPU",gather 负责"同时跑",缺一不可。

Jupyter 里直接 await,普通 .py 文件用 asyncio.run()

6.3 stream() --- 流式输出

逐 token 返回结果,实现"打字机效果":

python 复制代码
for chunk in llm.stream("请写一首关于春天的诗"):
    print(chunk.content, end="", flush=True)

flush=True 让内容立刻推到屏幕,不攒在缓冲区。适合聊天机器人、长文本生成等需要让用户看到进度的场景。

高级用法 astream_events 可以监听每个 token 的事件时间线:

python 复制代码
async for event in llm.astream_events("你好"):
    if event["event"] == "on_chat_model_stream":
        print(event["data"]["chunk"].content, end="", flush=True)

6.4 batch() --- 批量调用

一次给多个问题,LangChain 内部并行处理:

python 复制代码
questions = ["什么是 Python?", "什么是 JavaScript?", "什么是 Go?"]
responses = llm.batch(questions)
for q, r in zip(questions, responses):
    print(f"{q} → {r.content}")

适合批量处理独立请求、数据分析、内容生成。异步版用 abatch()

七、多平台接入实战

7.1 兼容 OpenAI 格式的平台

凡是兼容 OpenAI 接口的平台,直接用 ChatOpenAI,只改 base_urlapi_key 就行。这是 LangChain 统一接口理念最直观的体现。

python 复制代码
# CloseAI 代理(国内直连)
llm = ChatOpenAI(model="gpt-4o-mini")  
# 自动读 OPENAI_API_KEY 和 OPENAI_BASE_URL 环境变量

# DeepSeek
llm = ChatOpenAI(
    model="deepseek-chat",
    api_key=os.getenv("DEEPSEEK_API_KEY"),
    base_url="https://api.deepseek.com/v1",
)

# 硅基流动(50+ 开源模型)
llm = ChatOpenAI(
    model="Qwen/Qwen3-8B",
    api_key=os.getenv("SILICONFLOW_API_KEY"),
    base_url="https://api.siliconflow.cn/v1",
)

7.2 不兼容 OpenAI 格式的平台

Anthropic、Google 有自己的 API 格式,需要用专属类或 init_chat_model

python 复制代码
from langchain.chat_models import init_chat_model

# 一个函数统一管理所有平台
llm_openai = init_chat_model("gpt-5.4-nano-2026-03-17", model_provider="openai", ...)
llm_claude = init_chat_model("claude-opus-4-7", model_provider="anthropic", ...)
llm_gemini = init_chat_model("gemini-3.1-flash-lite-preview", model_provider="google_genai", ...)

# 调用方式一样
for llm in [llm_openai, llm_claude, llm_gemini]:
    print(llm.invoke("用一句话介绍你自己").content)

7.3 各平台速查表

平台 用哪个类 示例模型名 关键环境变量
OpenAI(CloseAI 代理) ChatOpenAI gpt-4o-mini OPENAI_API_KEY + OPENAI_BASE_URL
DeepSeek ChatOpenAI deepseek-chat DEEPSEEK_API_KEY
硅基流动 ChatOpenAI Qwen/Qwen3-8B SILICONFLOW_API_KEY
Anthropic ChatAnthropic claude-sonnet-4-20250514 ANTHROPIC_API_KEY
Google ChatGoogleGenerativeAI gemini-2.5-flash GOOGLE_API_KEY
Ollama(本地) ChatOllama qwen2.5:7b 无需 API Key

规律:兼容 OpenAI 格式的用 ChatOpenAI,不兼容的用 init_chat_model 或对应的专属类。

八、本地模型:Ollama

学习阶段频繁调 API 是一笔开销,Ollama 让你在本地跑模型,完全免费。

bash 复制代码
# 下载安装:https://ollama.com/download

# 下载并运行模型
ollama run qwen2.5:7b

# 查看已下载的模型
ollama list

LangChain 里调用:

python 复制代码
from langchain_ollama import ChatOllama

llm = ChatOllama(model="qwen2.5:7b", base_url="http://localhost:11434")
response = llm.invoke("你好,介绍一下你自己")
print(response.content)

API 的调用姿势和云端模型一模一样,改一行初始化即可。

九、几个值得了解的高级特性

9.1 多模态输入

支持图片输入的前提是用视觉语言模型(VLM),普通文本模型不行:

python 复制代码
import base64
from langchain_core.messages import HumanMessage

with open("image.jpg", "rb") as f:
    image_data = base64.b64encode(f.read()).decode()

message = HumanMessage(content=[
    {"type": "text", "text": "描述这张图片"},
    {"type": "image_url", "image_url": {
        "url": f"data:image/jpeg;base64,{image_data}"
    }}
])
response = llm.invoke([message])

Base64 编码把二进制图片转成纯文本,嵌在 JSON 里传输。注意区分:视觉模型只能"看懂"图片(比如 OCR 提取文字),视觉语言模型既能看懂图片内容也能用自然语言描述出来。

9.2 速率限制

当 API 有频率上限时,用 InMemoryRateLimiter 来自动排队:

python 复制代码
from langchain_core.rate_limiters import InMemoryRateLimiter

rate_limiter = InMemoryRateLimiter(requests_per_second=0.1)
llm = ChatOpenAI(model="gpt-4o-mini", rate_limiter=rate_limiter)

requests_per_second=0.1 表示 10 秒发一个请求,超出就自动等。

9.3 Token 用量追踪

想知道这次调用到底花了多少 token:

python 复制代码
from langchain_core.callbacks import get_usage_metadata_callback

with get_usage_metadata_callback() as cb:
    llm.invoke("你好")
    llm.invoke("再见")

print(cb.usage_metadata)
# {'input_tokens': ..., 'output_tokens': ..., 'total_tokens': ...}

9.4 提示词缓存

当你反复使用同一段很长的系统提示词时(比如 3000 字的角色设定),模型每次都要重新"读"一遍,费 token 又费时间。提示词缓存让服务商在服务器端缓存已处理的提示词,后续调用直接跳过重复计算。

  • OpenAI:全自动,你什么都不用做,API 自动识别相同前缀并缓存,命中后费用减半
  • Anthropic :需要显式标记,用 AnthropicPromptCachingMiddleware 中间件告诉 API 哪段可以缓存,命中后费用降低 90%
python 复制代码
# Anthropic 缓存中间件
from langchain_anthropic import ChatAnthropic, AnthropicPromptCachingMiddleware

llm = ChatAnthropic(
    model="claude-sonnet-4-20250514",
    middleware=[AnthropicPromptCachingMiddleware()]
)

注意这和 LLM 本地缓存(相同问题直接返回缓存结果,不调 API)是两回事。提示词缓存在服务端,缓存的是已计算的中间状态;本地缓存在你机器上,缓存的是完整的"问题→回答"键值对。

9.5 运行时动态切换模型

不重新初始化对象,通过 config 在调用时切换模型:

python 复制代码
configurable_model = init_chat_model(temperature=0)

result1 = configurable_model.invoke(
    "你好", config={"configurable": {"model": "gpt-4o-mini"}}
)
result2 = configurable_model.invoke(
    "你好", config={"configurable": {"model": "claude-sonnet-4-6"}}
)

这对 A/B 测试、多租户系统、根据用户选择切换模型的场景很方便。

十、小结

本节聚焦 Model I/O 的模型调用部分,核心就几件事:
#mermaid-svg-59cwhrAEDHYCR7K0{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}@keyframes edge-animation-frame{from{stroke-dashoffset:0;}}@keyframes dash{to{stroke-dashoffset:0;}}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-animation-slow{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 50s linear infinite;stroke-linecap:round;}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-animation-fast{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 20s linear infinite;stroke-linecap:round;}#mermaid-svg-59cwhrAEDHYCR7K0 .error-icon{fill:#552222;}#mermaid-svg-59cwhrAEDHYCR7K0 .error-text{fill:#552222;stroke:#552222;}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-thickness-normal{stroke-width:1px;}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-thickness-thick{stroke-width:3.5px;}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-pattern-solid{stroke-dasharray:0;}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-thickness-invisible{stroke-width:0;fill:none;}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-pattern-dashed{stroke-dasharray:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-pattern-dotted{stroke-dasharray:2;}#mermaid-svg-59cwhrAEDHYCR7K0 .marker{fill:#333333;stroke:#333333;}#mermaid-svg-59cwhrAEDHYCR7K0 .marker.cross{stroke:#333333;}#mermaid-svg-59cwhrAEDHYCR7K0 svg{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;}#mermaid-svg-59cwhrAEDHYCR7K0 p{margin:0;}#mermaid-svg-59cwhrAEDHYCR7K0 .edge{stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .section--1 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section--1 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section--1 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section--1 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section--1 path{fill:hsl(240, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section--1 text{fill:#ffffff;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon--1{font-size:40px;color:#ffffff;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge--1{stroke:hsl(240, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth--1{stroke-width:17;}#mermaid-svg-59cwhrAEDHYCR7K0 .section--1 line{stroke:hsl(60, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-0 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-0 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-0 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-0 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-0 path{fill:hsl(60, 100%, 73.5294117647%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-0 text{fill:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-0{font-size:40px;color:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-0{stroke:hsl(60, 100%, 73.5294117647%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-0{stroke-width:14;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-0 line{stroke:hsl(240, 100%, 83.5294117647%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-1 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-1 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-1 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-1 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-1 path{fill:hsl(80, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-1 text{fill:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-1{font-size:40px;color:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-1{stroke:hsl(80, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-1{stroke-width:11;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-1 line{stroke:hsl(260, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-2 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-2 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-2 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-2 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-2 path{fill:hsl(270, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-2 text{fill:#ffffff;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-2{font-size:40px;color:#ffffff;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-2{stroke:hsl(270, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-2{stroke-width:8;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-2 line{stroke:hsl(90, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-3 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-3 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-3 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-3 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-3 path{fill:hsl(300, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-3 text{fill:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-3{font-size:40px;color:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-3{stroke:hsl(300, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-3{stroke-width:5;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-3 line{stroke:hsl(120, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-4 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-4 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-4 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-4 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-4 path{fill:hsl(330, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-4 text{fill:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-4{font-size:40px;color:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-4{stroke:hsl(330, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-4{stroke-width:2;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-4 line{stroke:hsl(150, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-5 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-5 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-5 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-5 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-5 path{fill:hsl(0, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-5 text{fill:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-5{font-size:40px;color:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-5{stroke:hsl(0, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-5{stroke-width:-1;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-5 line{stroke:hsl(180, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-6 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-6 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-6 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-6 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-6 path{fill:hsl(30, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-6 text{fill:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-6{font-size:40px;color:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-6{stroke:hsl(30, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-6{stroke-width:-4;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-6 line{stroke:hsl(210, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-7 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-7 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-7 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-7 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-7 path{fill:hsl(90, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-7 text{fill:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-7{font-size:40px;color:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-7{stroke:hsl(90, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-7{stroke-width:-7;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-7 line{stroke:hsl(270, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-8 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-8 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-8 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-8 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-8 path{fill:hsl(150, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-8 text{fill:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-8{font-size:40px;color:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-8{stroke:hsl(150, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-8{stroke-width:-10;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-8 line{stroke:hsl(330, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-9 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-9 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-9 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-9 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-9 path{fill:hsl(180, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-9 text{fill:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-9{font-size:40px;color:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-9{stroke:hsl(180, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-9{stroke-width:-13;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-9 line{stroke:hsl(0, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-10 rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-10 path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-10 circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-10 polygon,#mermaid-svg-59cwhrAEDHYCR7K0 .section-10 path{fill:hsl(210, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-10 text{fill:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .node-icon-10{font-size:40px;color:black;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-edge-10{stroke:hsl(210, 100%, 76.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .edge-depth-10{stroke-width:-16;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-10 line{stroke:hsl(30, 100%, 86.2745098039%);stroke-width:3;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled circle,#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:lightgray;}#mermaid-svg-59cwhrAEDHYCR7K0 .disabled text{fill:#efefef;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-root rect,#mermaid-svg-59cwhrAEDHYCR7K0 .section-root path,#mermaid-svg-59cwhrAEDHYCR7K0 .section-root circle,#mermaid-svg-59cwhrAEDHYCR7K0 .section-root polygon{fill:hsl(240, 100%, 46.2745098039%);}#mermaid-svg-59cwhrAEDHYCR7K0 .section-root text{fill:#ffffff;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-root span{color:#ffffff;}#mermaid-svg-59cwhrAEDHYCR7K0 .section-2 span{color:#ffffff;}#mermaid-svg-59cwhrAEDHYCR7K0 .icon-container{height:100%;display:flex;justify-content:center;align-items:center;}#mermaid-svg-59cwhrAEDHYCR7K0 .edge{fill:none;}#mermaid-svg-59cwhrAEDHYCR7K0 .mindmap-node-label{dy:1em;alignment-baseline:middle;text-anchor:middle;dominant-baseline:middle;text-align:center;}#mermaid-svg-59cwhrAEDHYCR7K0 :root{--mermaid-font-family:"trebuchet ms",verdana,arial,sans-serif;} Model I/O

模型调用
模型选择
Chat Models 主流
LLMs 淘汰
Embeddings 不同用途
初始化
ChatOpenAI 最常用
init_chat_model 动态切换
核心参数
temperature 控制随机性
max_tokens 限制输出长度
timeout / max_retries
调用方式
invoke 同步
ainvoke 异步+并发
stream 逐token输出
batch 批量并行
跨平台
兼容OpenAI格式 → ChatOpenAI
不兼容 → init_chat_model
本地 → ChatOllama