【DataWhale-LLM】二、如何更好使用Prompt?

一、一些基本概念

1.prompt

如下图所示,大语言模型的输入就是prompt:
什么是prompt?

2.System prompt

就像我们上一篇文章提到的一样,我们可以设置一些内容影响模型的输出,这样的内容称为System prompt。比如说:

{
“system prompt”: “你是一个恋爱专家,接下来我扮演男方,你扮演女方,请告诉我该如何回答女生的问题”,
“user prompt”: “我今天不开心?”
}

二、接口准备(以通义千问为例)

1、设置API-KEY

如何获取通义千问API-KEY见上一篇

from getpass import getpass
DASHSCOPE_API_KEY = getpass()

2、设置环境变量

import os
os.environ["DASHSCOPE_API_KEY"] = DASHSCOPE_API_KEY

3、安装通义千问SDK

如果你已经按照第一章运行过,应该安装过这个包

pip install dashscope

4、定义一个函数,获取接口的输出

import random
from dashscope import Generation


def get_completion(messages):

    response = Generation.call("qwen-plus",
                               messages=messages,
                               # 设置随机数种子seed,如果没有设置,则随机数种子默认为1234
                               seed=random.randint(1, 10000),
                               # 将输出设置为"message"格式
                               result_format='message')
    print(response)
    return response.output.choices[0]['message']['content']

messages = [{'role': 'system', 'content': 'You are a helpful assistant.'},
            {'role': 'user', 'content': '如何做西红柿炒鸡蛋?'}]
s = get_completion(messages)
print(s)

三、如何设计 prompt

1、指令要清晰

1.1 使用分割符(这一块略过,暂时没挑出来,后边改)

1.2 结构化输出

按照JSON、HTML等格式输出内容。

messages = [{'role': 'system', 'content': 'You are a helpful assistant.'},
            {'role': 'user', 'content': f"""
请生成包括书名、作者和类别的三本虚构的、非真实存在的中文书籍清单,\
并以 JSON 格式提供,其中包含以下键:book_id、title、author、genre。
"""}]
print(get_completion(messages))

结果如下:

[
{
“book_id”: “1”,
“title”: “梦幻长河”,
“author”: “虚无墨客”,
“genre”: “奇幻小说”
},
{
“book_id”: “2”,
“title”: “星际迷航记”,
“author”: “宇宙旅人”,
“genre”: “科幻冒险”
},
{
“book_id”: “3”,
“title”: “古城秘事”,
“author”: “古风尘”,
“genre”: “历史悬疑”
}
]

1.3 判断是否满足条件

可以让大语言模型帮忙检查是否满足条件
如下所示:

text_1 = f"""
泡一杯茶很容易。首先,需要把水烧开。\
在等待期间,拿一个杯子并把茶包放进去。\
一旦水足够热,就把它倒在茶包上。\
等待一会儿,让茶叶浸泡。几分钟后,取出茶包。\
如果您愿意,可以加一些糖或牛奶调味。\
就这样,您可以享受一杯美味的茶了。
"""

messages = [{'role': 'system', 'content': 'You are a helpful assistant.'},
            {'role': 'user', 'content': f"""
您将获得由三个引号括起来的文本。\
如果它包含一系列的指令,则需要按照以下格式重新编写这些指令:
第一步 - ...
第二步 - …
…
第N步 - …
如果文本中不包含一系列的指令,则直接写“未提供步骤”。"
{text_1}
"""}]

response = get_completion(messages)
print("Text 1 的总结:")
print(response)

结果如下

Text 1 的总结:
第一步 - 把水烧开。
第二步 - 在等待水烧开期间,拿一个杯子并放入茶包。
第三步 - 当水足够热时,将其倒在茶包上。
第四步 - 等待一会儿,让茶叶浸泡。
第五步 - 几分钟后,取出茶包。
第六步 - 如有需要,可加入糖或牛奶调味。
第七步 - 享受您的茶。

接下来,我们试一下没有指令的情况

text_2 = f"""
今天阳光明媚,鸟儿在歌唱。\
这是一个去公园散步的美好日子。\
鲜花盛开,树枝在微风中轻轻摇曳。\
人们外出享受着这美好的天气,有些人在野餐,有些人在玩游戏或者在草地上放松。\
这是一个完美的日子,可以在户外度过并欣赏大自然的美景。
"""

messages = [{'role': 'system', 'content': 'You are a helpful assistant.'},
            {'role': 'user', 'content': f"""
您将获得由三个引号括起来的文本。\
如果它包含一系列的指令,则需要按照以下格式重新编写这些指令:
第一步 - ...
第二步 - …
…
第N步 - …
如果文本中不包含一系列的指令,则直接写“未提供步骤”。"
{text_2}
"""}]

response = get_completion(messages)
print("Text 2 的总结:")
print(response)

结果如下:

Text 2 的总结:
未提供步骤

1.4 提供少量示例

给顾名思义,给模型示例,让模型参考。示例如下:

messages = [{'role': 'system', 'content': 'You are a helpful assistant.'},
            {'role': 'user', 'content': f"""
你的任务是以一致的风格回答问题(注意:文言文和白话的区别)。
<学生>: 请教我何为耐心。
<老师>: 天生我材必有用,千金散尽还复来。
<学生>: 请教我何为坚持。
<老师>: 故不积跬步,无以至千里;不积小流,无以成江海。骑骥一跃,不能十步;驽马十驾,功在不舍。
<学生>: 请教我何为失败。
"""}]

response = get_completion(messages)
print(response)

答案如下:

<老师>: 胜败兵家常事,志在千里,烈士暮年,壮心不已。跌倒七次,起身八回,失败乃成功之母,坚韧之心,方能经受挫折之痛。

2、给模型时间思考

在prompt中加入逐步推理的要求,能让语言模型投入更多时间思考,输出的结果更合理。

2.1 制定步骤

如下所示:

text = f"""
在一个迷人的村庄里,兄妹杰克和吉尔出发去一个山顶井里打水。\
他们一边唱着欢乐的歌,一边往上爬,\
然而不幸降临——杰克绊了一块石头,从山上滚了下来,吉尔紧随其后。\
虽然略有些摔伤,但他们还是回到了温馨的家中。\
尽管出了这样的意外,他们的冒险精神依然没有减弱,继续充满愉悦地探索。
"""

messages = [{'role': 'system', 'content': 'You are a helpful assistant.'},
            {'role': 'user', 'content': f"""
1-用一句话概括下面用<>括起来的文本(中文)。
2-将摘要翻译成英语。
3-在英语摘要中列出每个名称。
4-输出一个 JSON 对象,其中包含以下键:English_summary,num_names。
请使用以下格式:
摘要:<摘要>
翻译:<摘要的翻译>
名称:<英语摘要中的名称列表>
输出 JSON 格式:<带有 English_summary 和 num_names 的 JSON 格式>
Text: <{text}>
"""}]
response = get_completion(messages)
print(response)

结果如下:

摘要:兄妹杰克和吉尔去山顶井打水,途中发生意外滚下山,但无大碍,仍保持冒险精神。
翻译:Jack and Jill, siblings, go up a hill to fetch water, have a mishap rolling down, but return home unharmed and maintain their adventurous spirit.
名称:Jack, Jill
输出 JSON 格式:{“English_summary”: “Jack and Jill, siblings, go up a hill to fetch water, have a mishap rolling down, but return home unharmed and maintain their adventurous spirit.”, “num_names”: 2}

2.2 指导模型在下结论前找自己的解法

如下所示:

messages = [{'role': 'system', 'content': 'You are a helpful assistant.'},
            {'role': 'user', 'content': f"""
判断学生的解决方案是否正确。
问题:
我正在建造一个太阳能发电站,需要帮助计算财务。
土地费用为 100美元/平方英尺
我可以以 250美元/平方英尺的价格购买太阳能电池板
我已经谈判好了维护合同,每年需要支付固定的10万美元,并额外支付每平方英尺10美元
作为平方英尺数的函数,首年运营的总费用是多少。
学生的解决方案:
设x为发电站的大小,单位为平方英尺。
费用:
土地费用:100x
太阳能电池板费用:250x
维护费用:100,000美元+100x
总费用:100x+250x+100,000美元+100x=450x+100,000美元
"""}]

response = get_completion(messages)
print(response)

结果如下:

学生的解决方案是正确的。他们正确地将各项费用作为平方英尺数x的函数来表示,并将它们相加得到总费用。总费用确实是土地费用、太阳能电池板费用和维护费用的和。

接下来,对模型进行更多指导:

messages = [{'role': 'system', 'content': 'You are a helpful assistant.'},
            {'role': 'user', 'content': f"""
请判断学生的解决方案是否正确,请通过如下步骤解决这个问题:
步骤:
首先,自己解决问题。
然后将您的解决方案与学生的解决方案进行比较,对比计算得到的总费用与学生计算的总费用是否一致,
并评估学生的解决方案是否正确。
在自己完成问题之前,请勿决定学生的解决方案是否正确。
使用以下格式:
问题:问题文本
学生的解决方案:学生的解决方案文本
实际解决方案和步骤:实际解决方案和步骤文本
学生计算的总费用:学生计算得到的总费用
实际计算的总费用:实际计算出的总费用
学生计算的费用和实际计算的费用是否相同:是或否
学生的解决方案和实际解决方案是否相同:是或否
学生的成绩:正确或不正确
问题:
我正在建造一个太阳能发电站,需要帮助计算财务。
- 土地费用为每平方英尺100美元
- 我可以以每平方英尺250美元的价格购买太阳能电池板
- 我已经谈判好了维护合同,每年需要支付固定的10万美元,并额外支付每平方英尺10美元;
作为平方英尺数的函数,首年运营的总费用是多少。
学生的解决方案:
设x为发电站的大小,单位为平方英尺。
费用:
1. 土地费用:100x美元
2. 太阳能电池板费用:250x美元
3. 维护费用:100,000+100x=10万美元+10x美元
总费用:100x美元+250x美元+10万美元+100x美元=450x+10万美元
实际解决方案和步骤:
"""}]

response = get_completion(messages)
print(response)

结果如下:
结果1

四、大模型缺陷:

幻觉,即它会产生一些虚假的信息,比如说:

messages = [{'role': 'system', 'content': 'You are a helpful assistant.'},
            {'role': 'user', 'content': f"""
给我一些研究LLM长度外推的论文,包括论文标题、主要内容和链接
"""}]

response = get_completion(messages)
print(response)

结果如下:

  1. 论文标题: “Long Short-Term Memory Network Extensions for Speech Recognition” 主要内容:
    这篇论文由Bengio等人在2014年发表,探讨了LSTM网络在语音识别中的应用,并提出了一些扩展,如双向LSTM和深度LSTM。他们展示了这些扩展如何改进模型的性能,特别是在处理长序列数据时。
    链接: https://arxiv.org/abs/1412.5567

  2. 论文标题:“A Theoretically Grounded Application of Dropout in Recurrent Neural Networks”
    主要内容:由Gal和Ghahramani在2016年发表,这篇论文提出了在LSTM中使用Dropout的技术,这是一种防止过拟合的有效方法。他们还提供了一种理论框架来理解和解释这种技术,特别是在处理长期依赖问题时的效果。
    链接:https://arxiv.org/abs/1512.05287

  3. 论文标题:“Hierarchical Multiscale Recurrent Neural Networks” 主要内容:由Le et
    al.在2015年提出,这篇论文引入了一种新的RNN结构,即分层多尺度RNN(HM-RNN),用于处理具有不同时间尺度的序列数据。这种方法可以看作是LSTM的一种扩展,对于处理复杂的长期依赖问题非常有效。
    链接:https://papers.nips.cc/paper/5951-hierarchical-multiscale-recurrent-neural-networks.pdf

  4. 论文标题:“Attention is All You Need” 主要内容:虽然这篇论文主要讨论的是Transformer模型,但其提出的自注意力机制在某种程度上是对LSTM长期依赖处理能力的扩展。Vaswani等人在2017年的这篇论文中提出,完全依赖自注意力机制的模型在机器翻译任务上超过了基于RNN的模型。
    链接:https://arxiv.org/abs/1706.03762

其中,部分论文的指向是存在问题的,这说明,有的时候大模型会胡言乱语。所以我们要利用好这个工具。

总结

主要讲了如何详细使用prompt生成更准确地结果

参考文献

阿里通义千问API
DataWhale-LLM-Universe课程地址

  • 24
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值