项目背景
划拳是汉族民间饮酒时一种助兴取乐的游戏,起源于汉代。
游戏规则如下:
两人同时伸出一只手,先攥起拳头,代表财不外露。再伸出一到五个手指,表示从零到五之间的数字,同时嘴里大声喊出两人所出数字之和。
两人都猜对或都猜错,则划拳继续。直到一方猜对才为赢家,而猜错方为输家,要罚酒。
这套酒令完整的说法是:"一条龙、哥俩好、三星照、四喜财、五魁首、六六六、七个巧、八匹马、九连环和十全有"。
在游戏中,我们借助大模型的强大能力,让大模型扮演你的划拳对手,玩家可以通过简单的操作与大模型进行划拳。
希望在你独自一人喝酒的时候,能通过这款游戏找到乐趣。
项目方案
划拳游戏的流程如下:
开始阶段: 两位玩家同时伸出一只手,用攥起的拳头和伸出一到五个手指表示从零到五这几个数字。 与此同时,两位玩家嘴里喊出从0到10的数字。
判断阶段: 比较两位玩家伸出的手指表示的数字相加的和与其中一位玩家嘴里喊出的数字是否相同。 如果相同,则喊出该数字的玩家获胜;如果不同,则继续下一轮。
惩罚阶段: 输的玩家需要按照规则喝酒或其他约定的惩罚。
我们希望模型扮演一个划拳游戏的玩家,核心是希望模型输出两个数字:出拳数字和猜拳数字。 核心prompt设计如下:
# 核心prompt
game_prompt = ("你现在在陪我玩划拳游戏,我已经出拳了,现在到你了。你的任务如下:"
"1.输出一个0-5之前的数字,表示你的出拳数字;"
"2.输出一个0-10之间的数字,表示你的猜拳数字;"
"3.将两个数字以{'gesture':'','predict':''}的JSON格式返回,其中gesture表示你的出拳数字,predict表示你的猜拳数字。"
"注意: 除了JSON格式数字以外,不要返回其他任何内容。")
代码实现
1. 安装项目依赖
In [1]
# 安装依赖
! pip install -U erniebot
Looking in indexes: https://mirror.baidu.com/pypi/simple/, https://mirrors.aliyun.com/pypi/simple/
Collecting erniebot
Downloading https://mirrors.aliyun.com/pypi/packages/b8/82/8bcbb280e13da2dd67667423d6ba34cb72f54c4201fb18816adc7de4914f/erniebot-0.5.3-py3-none-any.whl (65 kB)
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 65.9/65.9 kB 1.0 MB/s eta 0:00:00a 0:00:01
Requirement already satisfied: aiohttp in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from erniebot) (3.9.1)
Requirement already satisfied: bce-python-sdk in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from erniebot) (0.8.98)
Requirement already satisfied: colorlog in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from erniebot) (6.8.0)
Requirement already satisfied: jsonschema>=4.19 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from erniebot) (4.20.0)
Requirement already satisfied: requests>=2.20 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from erniebot) (2.31.0)
Collecting tenacity (from erniebot)
Downloading https://mirrors.aliyun.com/pypi/packages/f4/f1/990741d5bb2487d529d20a433210ffa136a367751e454214013b441c4575/tenacity-8.2.3-py3-none-any.whl (24 kB)
Requirement already satisfied: typing-extensions>=4.8.0 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from erniebot) (4.9.0)
Requirement already satisfied: attrs>=22.2.0 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from jsonschema>=4.19->erniebot) (23.1.0)
Requirement already satisfied: jsonschema-specifications>=2023.03.6 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from jsonschema>=4.19->erniebot) (2023.11.2)
Requirement already satisfied: referencing>=0.28.4 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from jsonschema>=4.19->erniebot) (0.32.0)
Requirement already satisfied: rpds-py>=0.7.1 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from jsonschema>=4.19->erniebot) (0.15.2)
Requirement already satisfied: charset-normalizer<4,>=2 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from requests>=2.20->erniebot) (3.3.2)
Requirement already satisfied: idna<4,>=2.5 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from requests>=2.20->erniebot) (3.6)
Requirement already satisfied: urllib3<3,>=1.21.1 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from requests>=2.20->erniebot) (2.1.0)
Requirement already satisfied: certifi>=2017.4.17 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from requests>=2.20->erniebot) (2023.11.17)
Requirement already satisfied: multidict<7.0,>=4.5 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from aiohttp->erniebot) (6.0.4)
Requirement already satisfied: yarl<2.0,>=1.0 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from aiohttp->erniebot) (1.9.4)
Requirement already satisfied: frozenlist>=1.1.1 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from aiohttp->erniebot) (1.4.1)
Requirement already satisfied: aiosignal>=1.1.2 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from aiohttp->erniebot) (1.3.1)
Requirement already satisfied: async-timeout<5.0,>=4.0 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from aiohttp->erniebot) (4.0.3)
Requirement already satisfied: pycryptodome>=3.8.0 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from bce-python-sdk->erniebot) (3.19.0)
Requirement already satisfied: future>=0.6.0 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from bce-python-sdk->erniebot) (0.18.3)
Requirement already satisfied: six>=1.4.0 in /opt/conda/envs/python35-paddle120-env/lib/python3.10/site-packages (from bce-python-sdk->erniebot) (1.16.0)
Installing collected packages: tenacity, erniebot
Successfully installed erniebot-0.5.3 tenacity-8.2.3
2.实现调用ERNIE API的方法
In [2]
import erniebot
# 调用ErnieBotSDK,实现智能对话
class ErnieLLM():
def __init__(self, token):
erniebot.api_type = 'aistudio'
erniebot.access_token = token
def predict(self, txt):
model = 'ernie-bot'
messages = [{'role': 'user', 'content': txt}]
response = erniebot.ChatCompletion.create(
model=model,
messages=messages,
)
return response.result
3.设计核心prompt
输入为空,输出为JSON格式的两个数字
In [3]
# 核心prompt
game_prompt = ("你现在在陪我玩划拳游戏,我已经出拳了,现在到你了。你的任务如下:"
"1.输出一个0-5之前的数字,表示你的出拳数字;"
"2.输出一个0-10之间的数字,表示你的猜拳数字;"
"3.将两个数字以{'gesture':'','predict':''}的JSON格式返回,其中gesture表示你的出拳数字,predict表示你的猜拳数字。"
"注意: 除了JSON格式数字以外,不要返回其他任何内容。")
4.获取模型输出并提取JSON字段
In [6]
import json
# 实现获取模型出拳和猜拳数字的方法
def predict_gesture(token):
# 请求文心一言模型的API
llm = ErnieLLM(token)
result = llm.predict(game_prompt)
# 提取JSON部分
start_index = result.find('{')
end_index = result.rfind('}') + 1
json_str = result[start_index:end_index]
# 将JSON字符串转换为Python字典
json_obj = json.loads(json_str)
return json_obj["gesture"], json_obj["predict"]
5.设计字典保存数字与酒令口号的映射关系,增加趣味性
In [11]
# 保存酒令口号与数字的映射关系
alias_dict = {
'一条龙': 1,
'哥俩好': 2,
'三星照': 3,
'四喜财': 4,
'五魁首': 5,
'六六六': 6,
'七个巧': 7,
'八匹马': 8,
'九连环': 9,
'十全有': 10
}
# 保存数字与酒令口号的映射关系
alias_dict_reverse = {v: k for k, v in alias_dict.items()}
6.实现判断游戏胜负的逻辑并进行测试
In [9]
def game_process(token, user_gesture, user_predict):
# 用户输入的出拳数字
user_num = int(user_gesture)
# 用户输入的猜拳数字
user_predict = int(alias_dict[user_predict])
# 调用模型进行预测
model_gesture, model_predict = predict_gesture(token)
# 计算双方出拳数字之和
total_fingers = user_num + int(model_gesture)
print(f"指数之和:{total_fingers}")
print(f"用户预测:{user_predict}")
print(f"模型预测:{model_predict}")
# 胜负判定
if user_predict == total_fingers and model_predict != total_fingers:
result = "我输了,自罚一杯!"
elif user_predict != total_fingers and model_predict == total_fingers:
result = "哈哈,你输了!请自罚一杯!"
else:
result = "平局!再来!"
return result, alias_dict_reverse[model_predict], model_gesture
In [13]
# 核心逻辑测试
print(game_process("替换为你的token",5,"八匹马"))
'ernie-bot' will be deprecated in the future. Please use 'ernie-3.5' instead.
指数之和:8
用户预测:8
模型预测:7
('我输了,自罚一杯!', '七个巧', 3)
7.利用gradio开发游戏原型
利用Comate进行辅助,参考代码如下
In [ ]
with gr.Blocks(title="划拳游戏", theme="soft") as game:
gr.Markdown("<center><h1>中国传统游戏--划拳</h1></center>")
gr.Markdown("""<center><p1>
中国传统酒令游戏"划拳"是两人同时伸出一只手,先攥起拳头,代表财不外露。再伸出一到五个手指,表示从零到五之间的数字,同时嘴里大声喊出两人所出数字之和。
两人都猜对或都猜错,则划拳继续。直到一方猜对才为赢家,而猜错方为输家,要罚酒的。唐朝人称划拳为"拇战"、"招手令"或"打令"等。一般都是从一开始,数到十结束。
这套酒令完整的说法是:"一条龙、哥俩好、三星照、四喜财、五魁首、六六六、七个巧、八匹马、九连环和十全有"。</p1>
</center>""")
token = gr.Textbox(label="AccessToken")
with gr.Row():
with gr.Column():
user_gesture = gr.Number(label="出拳(0-5之间的数字)", value=3)
user_predict = gr.Dropdown(label="猜拳",
choices=['一条龙', '哥俩好', '三星照', '四喜财', '五魁首', '六六六', '七个巧',
'八匹马', '九连环', '十全有'])
submit_button = gr.Button(value="Go!")
with gr.Column():
model_gesture = gr.Textbox(label="文心出拳")
model_predict = gr.Textbox(label="文心猜拳")
with gr.Row():
result = gr.Textbox(label="本轮结果")
submit_button.click(game_process, [token, user_gesture, user_predict], [result, model_predict, model_gesture])
comate 提效
星河社区最近上线支持在VSCode中一键启动Comate。在本项目代码编写过程中,我也体验了使用Comate辅助进行代码编写,极大提高了编码效率,给aistudio点赞👍。 具体的使用方法可以参考下面的链接:智能代码助手Comate上线星河社区
下面分享一下我使用comate的例子:
-
生成较为复杂的python字典
-
反转字段key、value
-
生成初步的gradio app页面
可以看到,生成的代码相当不错!我也是最近刚开始接触comate,更多使用方法让我们一起探索!
效果展示
游戏体验地址: https://aistudio.baidu.com/application/detail/24086
总结
通过ERNIE Bot SDK调用文心大模型的能力开发大模型应用是不是超简单?只需要将你的想法转化为合适的prompt,任何想法都能轻易实现!
不会写prompt?没关系!免费课程教你:https://aistudio.baidu.com/education/group/info/28604 快动动脑筋,行动起来吧!