模型输入 Prompts
一个语言模型的提示是用户提供的一组指令或输入,用于引导模型的响应,帮助它理解上下文并生成相关和连贯的基于语言的输出,例如回答问题、完成句子或进行对话。
- 提示模板(Prompt Templates):参数化的模型输入
- 示例选择器(Example Selectors):动态选择要包含在提示中的示例 fewshots 提示样例选择
提示模板 Prompt Templates
Prompt Templates 提供了一种预定义、动态注入、模型无关和参数化的提示词生成方式,以便在不同的语言模型之间重用模板。
一个模板可能包括指令、少量示例以及适用于特定任务的具体背景和问题。
通常,提示要么是一个字符串(LLMs),要么是一组聊天消息(Chat Model)。
类继承关系:
BasePromptTemplate --> PipelinePromptTemplate
StringPromptTemplate --> PromptTemplate
FewShotPromptTemplate
FewShotPromptWithTemplates
BaseChatPromptTemplate --> AutoGPTPrompt
ChatPromptTemplate --> AgentScratchPadChatPromptTemplate
BaseMessagePromptTemplate --> MessagesPlaceholder
BaseStringMessagePromptTemplate --> ChatMessagePromptTemplate
HumanMessagePromptTemplate
AIMessagePromptTemplate
SystemMessagePromptTemplate
PromptValue --> StringPromptValue
ChatPromptValue
使用 PromptTemplate 类生成提升词
通常,PromptTemplate 类的实例,使用Python的str.format语法生成模板化提示;也可以使用其他模板语法(例如jinja2)。
使用 from_template 方法实例化 PromptTemplate
from langchain import PromptTemplate
prompt_template = PromptTemplate.from_template(
"Tell me a {adjective} joke about {content}."
)
# 使用 format 生成提示
prompt = prompt_template.format(adjective="funny", content="chickens")
print(prompt)
# 输出样例
Tell me a funny joke about chickens.
使用构造函数(Initializer)实例化 PromptTemplate
使用构造函数实例化 prompt_template 时必须传入参数:input_variables 和 template。
在生成提示过程中,会检查输入变量与模板字符串中的变量是否匹配,如果不匹配,则会引发异常;
示例1
from langchain import PromptTemplate
from langchain_openai import OpenAI
import os
api_key = 'sk-xxx'
os.environ["OPENAI_API_KEY"] = api_key
serp_api = 'xxx'
os.environ["SERPAPI_API_KEY"] = serp_api
valid_prompt = PromptTemplate(
input_variables=["adjective", "content"],
template="Tell me a {adjective} joke about {content}"
)
prompt = valid_prompt.format(adjective="funny", content="chickens")
llm = OpenAI(model_name="gpt-3.5-turbo-instruct", max_tokens=1000)
result = llm(prompt)
print(f"result: {result}")
示例2
prompt_template = PromptTemplate.from_template(
"讲{num}个给程序员听得笑话"
)
from langchain_openai import OpenAI
llm = OpenAI(model_name="gpt-3.5-turbo-instruct", max_tokens=1000)
prompt = prompt_template.format(num=2)
print(f"prompt: {prompt}")
result = llm(prompt)
print(f"result: {result}")
使用 jinja2 生成模板化提示
from langchain import PromptTemplate
from langchain_openai import OpenAI
import os
api_key = 'sk-xx'
os.environ["OPENAI_API_KEY"] = api_key
serp_api = 'xxx'
os.environ["SERPAPI_API_KEY"] = serp_api
jinja2_template = "讲{{num}}个 给程序员听得笑话"
template_prompt = PromptTemplate.from_template(jinja2_template, template_format="jinja2")
prompt = template_prompt.format(num="2")
print(prompt)
llm = OpenAI(model_name="gpt-3.5-turbo-instruct", max_tokens=1000)
result = llm(prompt)
print(f"result: {result}")
使用 ChatPromptTemplate 类生成适用于聊天模型的聊天记录
ChatPromptTemplate 类的实例,使用format_messages方法生成适用于聊天模型的提示。
使用 from_messages 方法实例化 ChatPromptTemplate
import os
from langchain.prompts import ChatPromptTemplate
from langchain.chat_models import ChatOpenAI
api_key = 'sk-xx'
os.environ["OPENAI_API_KEY"] = api_key
serp_api = 'xxx'
os.environ["SERPAPI_API_KEY"] = serp_api
template = ChatPromptTemplate.from_messages([
("system", "You are a helpful AI bot. Your name is {name}."),
("human", "Hello, how are you doing?"),
("ai", "I'm doing well, thanks!"),
("human", "{user_input}"),
])
# 生成提示
messages = template.format_messages(
name="Bob",
user_input="What is your name?"
)
print(messages)
chat_model = ChatOpenAI(model_name="gpt-3.5-turbo", max_tokens=1000)
result = chat_model(messages)
print(result)
摘要总结
import os
from langchain.prompts import ChatPromptTemplate
from langchain.chat_models import ChatOpenAI
api_key = 'sk-xxx'
os.environ["OPENAI_API_KEY"] = api_key
serp_api = 'xxxx'
os.environ["SERPAPI_API_KEY"] = serp_api
summary_template = ChatPromptTemplate.from_messages([
("system", "你将获得关于同一主题的{num}篇文章(用-----------标签分隔)。首先总结每篇文章的论点。然后指出哪篇文章提出了更好的论点,并解释原因。"),
("human", "{user_input}"),
])
# 生成提示
messages = summary_template.format_messages(
num=3,
user_input='''1. [PHP是世界上最好的语言]
PHP是世界上最好的情感派编程语言,无需逻辑和算法,只要情绪。它能被蛰伏在冰箱里的PHP大神轻易驾驭,会话结束后的感叹号也能传达对代码的热情。写PHP就像是在做披萨,不需要想那么多,只需把配料全部扔进一个碗,然后放到服务器上,热乎乎出炉的网页就好了。
-----------
2. [Python是世界上最好的语言]
Python是世界上最好的拜金主义者语言。它坚信:美丽就是力量,简洁就是灵魂。Python就像是那个永远在你皱眉的那一刻扔给你言情小说的好友。只有Python,你才能够在两行代码之间感受到飘逸的花香和清新的微风。记住,这世上只有一种语言可以使用空格来领导全世界的进步,那就是Python。
-----------
3. [Java是世界上最好的语言]
Java是世界上最好的德育课编程语言,它始终坚守了严谨、安全的编程信条。Java就像一个严格的老师,他不会对你怀柔,不会让你偷懒,也不会让你走捷径,但他教会你规范和自律。Java就像是那个喝咖啡也算加班费的上司,拥有对邪恶的深度厌恶和对善良的深度拥护。
'''
)
print(messages)
chat_model = ChatOpenAI(model_name="gpt-3.5-turbo", max_tokens=1000)
result = chat_model(messages)
print(result)
使用 FewShotPromptTemplate 类生成 Few-shot Prompt
构造 few-shot prompt 的方法通常有两种:
- 方法1 从示例集(set of examples)中手动选择;
- 方法2 通过示例选择器(Example Selector)自动选择.
示例选择器 Example Selectors
如果你有大量的参考示例,就得选择哪些要包含在提示中。最好还是根据某种条件或者规则来自动选择,Example Selector 是负责这个任务的类。
BaseExampleSelector 定义如下:
class BaseExampleSelector(ABC):
"""用于选择包含在提示中的示例的接口。"""
@abstractmethod
def select_examples(self, input_variables: Dict[str, str]) -> List[dict]:
"""根据输入选择要使用的示例。"""
ABC 是 Python 中的 abc 模块中的一个缩写,它表示 "Abstract Base Class"(抽象基类)。在 Python 中,抽象基类用于定义其他类必须遵循的基本接口或蓝图,但不能直接实例化。其主要目的是为了提供一种形式化的方式来定义和检查子类的接口。
使用抽象基类的几点关键信息:
- 抽象方法:在抽象基类中,你可以定义抽象方法,它没有实现(也就是说,它没有方法体)。任何继承该抽象基类的子类都必须提供这些抽象方法的实现。
- 不能直接实例化:你不能直接创建抽象基类的实例。试图这样做会引发错误。它们的主要目的是为了被继承,并在子类中实现其方法。
- 强制子类实现:如果子类没有实现所有的抽象方法,那么试图实例化该子类也会引发错误。这确保了继承抽象基类的所有子类都遵循了预定的接口。