Skip to content

Prompt(提示词)

Prompt 提示词是向模型提供输入的过程。输出质量常常取决于你能多好地对模型进行提示。提示词既是艺术也是科学。OpenAI 提供了一些策略与 API 设计,帮助你构建更强的提示词并从模型获得稳定的好结果。鼓励你进行实验。

提示词的工具与技巧

  • 提示词缓存(Prompt caching):可将延迟最高降低约 80%、成本最高降低约 75%。
  • 提示词工程(Prompt engineering):用于构建提示词的策略、技术与工具。

创建提示词

登录并使用 OpenAI 控制台来创建、保存、版本化并分享你的提示词。

  1. 开始创建提示词
    在 Playground 中填写字段以创建你期望的提示词。

  2. 添加提示词变量
    变量允许你在不更改提示词文本的情况下注入动态值。在任意消息角色中以 使用变量。示例:当创建“本地天气”提示词时,可以添加 city 变量,其值为 San Francisco

  3. 在 Responses API 调用中使用提示词
    在控制台 URL 中找到提示词的 ID 与版本号,并以 prompt_id 传入:

bash
curl -s -X POST "https://api.openai.com/v1/responses"   -H "Content-Type: application/json"   -H "Authorization: Bearer $OPENAI_API_KEY"   -d '{
    "prompt": {
      "prompt_id": "pmpt_123",
      "variables": {
        "city": "San Francisco"
      }
    }
  }'
  1. 创建新的提示词版本
    通过版本化迭代提示词,而不覆盖既有细节。你可以在 API 中使用所有版本,并相互评估其表现。若未指定版本,提示词 ID 指向最新发布版本。
    要创建新版本:编辑提示词并点击“Update”。你会获得一个新的提示词 ID 以用于 Responses API 调用。

  2. 需要时回滚
    在提示词控制台中选择要回滚的提示词。右侧点击“History”,找到希望恢复的版本,点击“Restore”。

如何优化提示词

  • 将整体语气或角色指引放在系统消息;将任务细节与示例放在用户消息。
  • 将 few-shot 示例合并为简洁的 YAML 风格或条目块,以便扫描与更新。
  • 用清晰的文件/文件夹命名映射你的项目结构,方便团队快速定位提示词。
  • 每次发布后重跑关联的评测,尽早发现问题比在生产中修复更省成本。

提示词缓存

使用提示词缓存以降低延迟与成本。

模型提示词常包含重复内容(如系统提示与常用指令)。OpenAI 会将 API 请求路由到最近处理过相同提示词的服务器,使得相较于从零处理更便宜且更快速。提示词缓存可将延迟最高降低约 80%,将输入 token 成本最高降低约 90%。提示词缓存在所有 API 请求中自动生效(无需代码更改),且无额外费用。提示词缓存适用于所有近期模型(gpt-4o 及之后)。

本指南说明提示词缓存的工作原理,以便你优化提示词从而获得更低延迟与成本。

如何组织提示词以更好命中

只有提示词的完全一致的前缀才会命中缓存。为了获得缓存收益,应将静态内容(说明、示例等)放在提示词开头,将变量内容(如用户特定信息)放在末尾。这同样适用于图像与工具:它们在不同请求之间必须保持一致。

(原文有可视化示意图,已省略外链图像)

工作方式

当提示词长度达到 1024 tokens 或更长时会启用缓存。一次 API 请求会经历以下步骤:

  1. 缓存路由(Cache Routing)

    • 请求会基于提示词前缀的哈希被路由到某台机器。该哈希通常使用前 256 个 token(具体长度依模型而异)。
    • 如提供 prompt_cache_key 参数,它会与前缀哈希组合,让你可以影响路由并提升命中率;当许多请求共享长、相同前缀时,尤为有用。
    • 若同一“前缀 + prompt_cache_key”组合的请求速率超过约每分钟 15 次,部分请求会溢出到额外机器,降低缓存效果。
  2. 缓存查找(Cache Lookup)
    系统检查所选机器上是否存在该提示词前缀的缓存。

  3. 缓存命中(Cache Hit)
    若存在匹配前缀,则使用缓存结果,从而显著降低延迟并减少成本。

  4. 缓存未命中(Cache Miss)
    若未命中,将完整处理整个提示词;处理后会在该机器上缓存此前缀,以供后续复用。

通常情况下,缓存前缀在5–10 分钟无活动后会被清理;但在低峰期可能保留至一小时

启用要求

缓存适用于**≥ 1024 tokens** 的提示词;命中按每 128 tokens 递增。因此可缓存的 token 数将落在如下序列:1024、1152、1280、1408、……,取决于提示词长度。

所有请求(包括少于 1024 tokens 的)都会在响应对象的 usage.prompt_tokens_details.cached_tokens 字段展示缓存命中数;少于 1024 tokens 时该值为 0。

json
"usage": {
  "prompt_tokens": 2006,
  "completion_tokens": 300,
  "total_tokens": 2306,
  "prompt_tokens_details": {
    "cached_tokens": 1920
  },
  "completion_tokens_details": {
    "reasoning_tokens": 0,
    "accepted_prediction_tokens": 0,
    "rejected_prediction_tokens": 0
  }
}

可缓存内容

  • 消息:完整的 messages 数组(系统、用户、助手等)。
  • 图像:包含在用户消息中的图像(链接或 base64,多图均可);需确保 detail 参数一致,因为它会影响图像的分词。
  • 工具使用:messages 与 tools 列表也可被缓存,并计入 1024 token 阈值。
  • 结构化输出:结构化输出的 schema 作为系统消息前缀同样可缓存。

最佳实践

  • 静态或重复内容起头,动态或用户特定内容置于末尾。
  • 在共享公共前缀的请求中一致使用 prompt_cache_key;选择合理粒度,使每个“前缀 + 键”的组合保持在每分钟约 15 次以下,避免溢出。
  • 监控缓存性能指标:命中率、延迟、被缓存 token 占比等,并据此优化。
  • 保持稳定的相同前缀请求流,降低缓存驱逐,最大化收益。

常见问题

  1. 如何保障缓存的数据隐私?
    缓存不会在不同组织间共享;只有同一组织的相同提示词才能彼此命中。

  2. 提示词缓存是否影响输出 token 的生成或最终响应?
    不影响。缓存仅针对提示词本身;输出每次仍会重新计算。

  3. 可以手动清除缓存吗?
    目前不支持。缓存会按最近使用时间自动清理;典型的清理窗口为 5–10 分钟不活跃,低峰期可达一小时。

  4. 使用提示词缓存是否需要额外付费?
    不需要。提示词缓存自动启用、无额外费用。

  5. 被缓存的提示词是否计入速率限制(TPM)?
    是的;缓存不改变速率限制策略。

  6. 提示词缓存是否支持零数据保留(Zero Data Retention)?
    支持;它与现有零数据保留策略兼容。


提示词工程

使用 OpenAI API,可像在 ChatGPT 中那样通过提示词生成文本。模型几乎可生成任意类型的文本响应:代码、数学表达式、结构化 JSON 数据或类人类的自然语言。

以下是使用 Responses API 的简例:

javascript
import OpenAI from "openai";
const client = new OpenAI();

const response = await client.responses.create({
  model: "gpt-5",
  input: "Write a one-sentence bedtime story about a unicorn."
});

console.log(response.output_text);
python
from openai import OpenAI
client = OpenAI()

response = client.responses.create(
  model="gpt-5",
  input="Write a one-sentence bedtime story about a unicorn."
)

print(response.output_text)
csharp
using OpenAI.Responses;

string key = Environment.GetEnvironmentVariable("OPENAI_API_KEY")!;
OpenAIResponseClient client = new(model: "gpt-5", apiKey: key);

OpenAIResponse response = client.CreateResponse(
  "Write a one-sentence bedtime story about a unicorn."
);

Console.WriteLine(response.GetOutputText());
bash
curl "https://api.openai.com/v1/responses"   -H "Content-Type: application/json"   -H "Authorization: Bearer $OPENAI_API_KEY"   -d '{
    "model": "gpt-5",
    "input": "Write a one-sentence bedtime story about a unicorn."
  }'

模型生成的内容位于响应的 output 属性中。在本例中数组里只有一个条目,类似:

json
[
  {
    "id": "msg_67b73f697ba4819183a15cc17d011509",
    "type": "message",
    "role": "assistant",
    "content": [
      {
        "type": "output_text",
        "text": "Under the soft glow of the moon, Luna the unicorn danced through fields of twinkling stardust, leaving trails of dreams for every child asleep.",
        "annotations": []
      }
    ]
  }
]

output 数组往往包含多于一个的条目。 它可能含有工具调用、关于推理模型的 reasoning token 数据等。因此不要假设文本一定位于 output[0].content[0].text

部分官方 SDK 提供了 output_text 便捷属性,会将所有文本输出聚合为单个字符串。

除了纯文本外,你还可以让模型以 JSON 形式返回结构化数据(Structured Outputs)。

选择模型

在通过 API 生成内容时,一个关键选择是使用哪个模型(model 参数)。完整清单见模型文档。几点考量:

  • 推理模型:会生成内部思维链来分析输入提示词,擅长复杂任务与多步规划;通常比 GPT 模型更慢也更昂贵。
  • GPT 模型:速度快、性价比高、智能强,但更依赖明确说明任务细节的指令。
  • 大模型与小模型(mini 或 nano):在速度、成本、智能之间做权衡。大模型对跨领域的理解与问题求解更稳健,小模型通常更快更便宜。

若拿不准,可选综合平衡较好的模型快照。

提示词工程

提示词工程是为模型撰写有效指令,使其稳定地产出符合要求内容的过程。由于生成是非确定性的,提示词既是艺术也是科学;不过可以应用一些技术与最佳实践以获得更稳定的好结果。

有些技巧对所有模型都有效,如使用消息角色。但不同模型类型(推理 vs GPT)或同一系列内不同快照,往往需要差异化的提示策略。因此在构建更复杂的应用时,强烈建议:

  • 在生产中将应用固定到具体的模型快照,以确保行为一致;
  • 构建**评测(evals)**来衡量提示词行为,以便在迭代或更换模型版本时监控提示词表现。

下面介绍可用于构建提示词的工具与技术。

消息角色与指令跟随

可通过 instructions 参数或消息角色向模型提供不同“权威等级”的指令。

  • instructions:提供高层次的生成行为指引,包括语气、目标与正确响应示例。通过该参数提供的指令优先级高于 input 中的提示词。

使用 instructions 生成文本

javascript
import OpenAI from "openai";
const client = new OpenAI();

const response = await client.responses.create({
  model: "gpt-5",
  reasoning: { effort: "low" },
  instructions: "Talk like a pirate.",
  input: "Are semicolons optional in JavaScript?",
});

console.log(response.output_text);

上面的例子大致等价于在 input 数组中使用以下消息:

使用不同角色的消息生成文本

javascript
import OpenAI from "openai";
const client = new OpenAI();

const response = await client.responses.create({
  model: "gpt-5",
  reasoning: { effort: "low" },
  input: [
    { "role": "developer", "content": "Talk like a pirate." },
    { "role": "user", "content": "Are semicolons optional in JavaScript?" }
  ],
});

console.log(response.output_text);

注意:instructions 参数仅适用于当前响应生成请求。若你用 previous_response_id 管理会话状态,则上一轮的 instructions 不会自动出现在当前上下文中。

消息角色的优先级(链式指挥)概要

developeruserassistant
开发者消息:由应用开发者提供,优先级高于用户消息。用户消息:由最终用户提供,优先级低于开发者消息。助手消息:由模型生成。

多轮对话可能由多条这类消息构成,以及你和模型提供的其他内容类型。

可以把 developeruser 消息分别类比为编程语言中的函数定义函数参数

  • developer 消息用于提供系统规则与业务逻辑;
  • user 消息提供被应用在这些规则之上的输入与配置。

可复用提示词

在控制台中,你可以开发可复用的提示词,并直接在 API 请求中使用 prompt 参数替代在代码中编写提示文本。借此更易于构建与评估提示词,并在无需修改集成代码的情况下部署改进版本。

工作方式如下:

  1. 在控制台中创建可复用提示词,使用占位符如
  2. 在 API 请求中使用该提示词prompt 参数对象包含以下属性):
    • id:提示词唯一标识;
    • version:提示词的特定版本(默认使用控制台标记为“current”的版本);
    • variables:对提示词中变量的替换映射。替换值可以是字符串,也可以是其他输入类型(如 input_imageinput_file 等)。

字符串变量示例

javascript
import OpenAI from "openai";
const client = new OpenAI();

const response = await client.responses.create({
  model: "gpt-5",
  prompt: {
    id: "pmpt_abc123",
    version: "2",
    variables: {
      customer_name: "Jane Doe",
      product: "40oz juice box"
    }
  }
});

console.log(response.output_text);

带文件输入的变量示例

javascript
import fs from "fs";
import OpenAI from "openai";
const client = new OpenAI();

// 上传一个稍后在变量中引用的 PDF
const file = await client.files.create({
  file: fs.createReadStream("draconomicon.pdf"),
  purpose: "user_data",
});

const response = await client.responses.create({
  model: "gpt-5",
  prompt: {
    id: "pmpt_abc123",
    variables: {
      topic: "Dragons",
      reference_pdf: {
        type: "input_file",
        file_id: file.id
      }
    }
  }
});

console.log(response.output_text);

用 Markdown 与 XML 组织提示

在编写 developeruser 消息时,你可以使用 Markdown 来标注提示词中的逻辑边界与层次;也可以用 XML 标签来界定一段引用材料的起止,或通过 XML 属性附带元数据,方便在指令中引用。

一般来说,一个 developer 消息包含下列部分(通常按此顺序,但最佳做法可能因模型而异):

  • Identity:描述助手的目的、沟通风格与高层目标;
  • Instructions:给出生成规则与禁止事项;若需要调用自定义函数,也在此说明;
  • Examples:示例输入与期望输出;
  • Context:与任务相关的其他信息(如训练数据之外的私有/专有数据),通常置于提示词靠后位置,便于为不同生成请求替换不同上下文。

示例提示词(用于代码生成)

text
# Identity

You are coding assistant that helps enforce the use of snake case 
variables in JavaScript code, and writing code that will run in 
Internet Explorer version 6.

# Instructions

* When defining variables, use snake case names (e.g. my_variable) 
  instead of camel case names (e.g. myVariable).
* To support old browsers, declare variables using the older 
  "var" keyword.
* Do not give responses with Markdown formatting, just return 
  the code as requested.

# Examples

<user_query>
How do I declare a string variable for a first name?
</user_query>

<assistant_response>
var first_name = "Anna";
</assistant_response>

API 请求

javascript
import fs from "fs/promises";
import OpenAI from "openai";
const client = new OpenAI();

const instructions = await fs.readFile("prompt.txt", "utf-8");

const response = await client.responses.create({
  model: "gpt-5",
  instructions,
  input: "How would I declare a variable for a last name?",
});

console.log(response.output_text);

用提示词缓存节约成本与延迟

构造消息时,应将你期望在多次 API 请求中复用的内容放在提示词的前部,并尽量作为请求体中的前几个参数传入,以最大化来自提示词缓存的收益。

Few-shot 少样本学习

Few-shot 允许你通过在提示词中包含少量输入/输出示例来把模型引导到一个新任务上,而无需微调。模型会从示例中隐式学习模式并应用于当前提示词。提供示例时,尽量覆盖多样输入及期望输出。

通常,你会把示例放在 API 请求中的 developer 消息部分。以下是一个对“客服评论情感分类(Positive/Negative/Neutral)”进行 few-shot 的示例 developer 消息:

text
# Identity

You are a helpful assistant that labels short product reviews as
Positive, Negative, or Neutral.

# Instructions

* Only output a single word in your response with no additional formatting
  or commentary.
* Your response should only be one of the words "Positive", "Negative", or
  "Neutral" depending on the sentiment of the product review you are given.

# Examples

<product_review id="example-1">
I absolutely love this headphones — sound quality is amazing!
</product_review>

<assistant_response id="example-1">
Positive
</assistant_response>

<product_review id="example-2">
Battery life is okay, but the ear pads feel cheap.
</product_review>

<assistant_response id="example-2">
Neutral
</assistant_response>

<product_review id="example-3">
Terrible customer service, I'll never buy from them again.
</product_review>

<assistant_response id="example-3">
Negative
</assistant_response>

包含相关上下文信息

在提示词中加入模型可用来生成响应的附加上下文通常很有帮助:

  • 给模型访问专有/私有数据或任何训练数据之外的数据;
  • 将模型的响应限制在一组你预先选定的资源中。

这种在生成请求中注入额外相关上下文的技术有时被称为 RAG(检索增强生成)。你可以通过向量数据库检索并把返回的文本加入提示词,或使用文件搜索功能,基于已上传文档生成内容。

规划上下文窗口

模型在一次生成请求中只能处理有限数据,这个内存上限称为上下文窗口,按 token 计量。不同模型具有不同大小的上下文窗口,从十几万到更大。请参考模型文档选择合适的上下文窗口,并在提示词中控制上下文长度。

提示推理模型

与 GPT 模型相比,推理模型在只有高层指导的情况下通常能给出更好的结果;而 GPT 模型更受益于明确而精细的指令。可以这样类比:

  • 推理模型像资深同事:给出一个目标,就能自行找出完成的细节路径;
  • GPT 模型像初级同事:在提供明确步骤、格式与约束时表现最佳。