引言:对于接口,不了解参数含义,就不知道它能咋用?而了解参数的含义最好有例子,基于这个认知,整理了OpenAI几个主要API的接口参数说明。
OpenAI的ChatCompletion和Completion都是自然语言生成模型的接口,但它们的用途和应用场景略有不同。
ChatCompletion | Completion | |
---|---|---|
区别 | 专为生成对话和聊天场景而设计。 | 是一个通用的自然语言生成接口,支持生成各种类型的文本,包括段落、摘要、建议、答案等等。 |
适用场景 | ChatCompletion接口生成的文本通常会更具有人类对话的风格和语调,可以用于智能客服、聊天机器人等场景,以及在日常聊天中帮助用户自动生成回复。 | Completion接口的输出更为多样化,可能会更加严谨和专业,适用于各种文本生成场景,例如文章创作、信息提取、机器翻译、自然语言问题回答等等。 |
总之:
- ChatCompletion适用于生成对话和聊天场景的文本,
- Completion则适用于更为广泛的自然语言生成场景。
使用例子
由于两个的接口参数基本一致,我们这里就只通过例子介绍不一样的,通用部分请看:OpenAI.Completion.create 接口参数说明
参数 messages
ChatCompletion将一系列消息作为输入,并返回模型生成的消息作为输出。
示例 API 调用如下所示:
# Note: you need to be using OpenAI Python v0.27.0 for the code below to work
import openai
openai.ChatCompletion.create(
model="gpt-3.5-turbo",
messages=[
{"role": "system", "content": "You are a helpful assistant."},
{"role": "user", "content": "Who won the world series in 2020?"},
{"role": "assistant", "content": "The Los Angeles Dodgers won the World Series in 2020."},
{"role": "user", "content": "Where was it played?"}
]
)
messages必须是消息对象的数组,其中每个对象都有一个角色(“system”、“user”、“assistant”)和内容(消息的内容)。对话可以短至 1 条消息或填满许多页面。
通常,对话的格式首先是system消息,然后是交替的user和assistant消息。
-
system消息有助于设置聊天AI助手的行为。在上面的例子中,被指示“你是一个乐于助人的助手”。
-
user消息有助于指示助手。它们可以由应用程序的最终用户生成,也可以由开发人员设置为指令。
-
assistant消息有助于存储先前的响应。它们也可以由开发人员编写,以帮助提供所需行为的示例。
上下文消息引用
因为请求是无状态的(模型没有过去请求的记忆),引用以前的消息(对话历史记录)会帮助AI理解上下文。比如在上面的例子中,用户的最后一个问题“在哪里开的?”只有在之前关于2020年世界大赛的消息的上下文中才有意义。
如果对话受token长度的限制,需要以某种方式缩短它。下面是徐文浩封装的一个例子,我们可以看到解决token长度的一个简单方法:
出处: https://time.geekbang.com/column/article/643915
https://github.com/xuwenhao/geektime-ai-course/blob/main/06_chatgpt_and_application.ipynb
import openai
import os
openai.api_key = os.environ.get("OPENAI_API_KEY")
class Conversation:
def __init__(self, prompt, num_of_round):
self.prompt = prompt
self.num_of_round = num_of_round
self.messages = []
self.messages.append({"role": "system", "content": self.prompt})
def ask(self, question):
try:
self.messages.append({"role": "user", "content": question})
response = openai.ChatCompletion.create(
model="gpt-3.5-turbo",
messages=self.messages,
temperature=0.5,
max_tokens=2048,
top_p=1,
)
except Exception as e:
print(e)
return e
message = response["choices"][0]["message"]["content"]
self.messages.append({"role": "assistant", "content": message})
if len(self.messages) > self.num_of_round*2 + 1:
del self.messages[1:3] //Remove the first round conversation left.
return message
在上面例子请求里,会把最新的问题拼接到整个对话数组的最后,在得到 ChatGPT 的回答之后也会把回答拼接上去。
如果回答完之后,发现会话的轮数超过设置的 num_of_round,就去掉最前面的一轮会话。
这种方式可以方便的让AI了解必须的上下文,但是要注意token的收费模式,越往后面,我们发送的token越多,收费越多。
返回参数 finish_reason
最前面示例 API 响应返回如下所示:
{
'id': 'chatcmpl-6p9XYPYSTTRi0xEviKjjilqrWU2Ve',
'object': 'chat.completion',
'created': 1677649420,
'model': 'gpt-3.5-turbo',
'usage': {'prompt_tokens': 56, 'completion_tokens': 31, 'total_tokens': 87},
'choices': [
{
'message': {
'role': 'assistant',
'content': 'The 2020 World Series was played in Arlington, Texas at the Globe Life Field, which was the new home stadium for the Texas Rangers.'},
'finish_reason': 'stop',
'index': 0
}
]
}
返回信息中包含finish_reason这个参数,它的值可能是下面几个:
- stop:API 返回完整的模型输出
- length:由于参数或令牌限制max_tokens模型输出不完整
- content_filter:由于内容过滤器中的标志而遗漏了内容
- null:API 响应仍在进行中或不完整
这个值可以帮助我们了解一些特殊情况返回的原因。
总结
ChatCompletion接口是专为生成对话和聊天场景而设计,由于接口是无状态,在请求时我们需要带上上下文,这时候要合理使用,避免越往后面收费越贵。