架构简析| 让智能体自己生成故事

WhatIfGPT概述

WhatIfGPT尝试用多个Agents之间的互动来自动生成故事. 项目里使用了一个故事讲述Agent,和多个角色Agents。故事讲述Agents负责和角色Agents交流,并旁叙故事。项目可以自定义故事主题、角色数量。故事讲述Agent和角色Agent都有记忆模块。项目会自动设立故事的目标,角色Agents会尝试达成目标,故事讲述Agent会在每轮讲述后检查目标是否达成。

WhatIfGPT工作流程如下:

在这里插入图片描述

  1. Story Settings --> Run:设定故事主题(story),如哈利·波特、加勒比海盗等,角色代理的数量,让GPT自动生成或手工设定每个角色名字(agent_names)和整个故事设定(story_setting_event)。点击Run按钮,开始生成故事,不需要用户再输入任何内容。
  2. Generate Main Stroy --> Stroyteller Narrates Main Story:根据用户输入的基本信息,进一步细化故事背景、故事人物等信息。
    1. 根据故事主题生成指定数量的角色代理,代理继承了LangChain的GenerativeAgent扩展类,使用下面给出的Prompt1(随机创建角色略有不同)创建角色的的性别、年龄等基本特征,并赋予记忆。
    2. 根据之前故事主题角色名字故事设定, 用prompt2让GPT生成一个故事起点(specified_story),指示角色接下来的行动,并用prompt3从中生成一个故事最终目标(story_main_objective)。
    3. 创建故事讲述者代理的实例和角色代理的实例。放入更具体的讲述者的System Prompt,角色的System Prompt。
# primpt1 
f"基于{story}角色 {name}拥有一些基本的记忆和事件,"  
"以JSON格式提供以下属性:\n"  
"name: 角色的名字\n"  
"race: 角色的种族\n"  
"sex: 角色的性别\n"  
"age: 角色的年龄\n"  
"traits: 描述角色的3到8个特征(用逗号分隔)\n"  
f"status: 从{story}的角度看角色的当前状态\n"  
f"daily_summaries: 今天角色完成的5到10个{mood}主题的日常活动(字符串数组)\n"  
f"memories: 角色生活中的5到10个{mood}主题的回忆(字符串数组)\n"

# Prompt2 生成故事
f"""
这基于 {story}.  
角色是: {', '.join(agent_names)}.  
故事设定: {story_setting_event}"

叙述一段富有创意和激动人心的背景故事,这个故事从未被讲述过,并为故事的主要目标做好铺垫。  
主要目标必须需要角色完成一系列的任务。  
如果主要目标是物品或人,为他们取一个富有创意和酷炫的名字。  
具体地叙述开始这个旅程的下一步应该是什么。  
{', '.join(agent_names)}还没有采取任何行动,只提供故事的介绍和背景。  
请用100字或更少的词回答指定的任务。  
直接向角色说话: {', '.join(agent_names)}。  
不要添加任何其他内容。"""

# Prompt3 抽取故事目标,specified_story是上么Promt生成的故事内容
f"""以下是故事: {specified_story}  
这个故事的主要目标是什么 {', '.join(agent_names)}? 一行内叙述回答,不要添加任何其他内容。"""

# 故事讲述者代理的System Prompt
f"""
这基于 {story}.  
角色是: {', '.join(agent_names)}.  
故事设定: {story_setting_event}"

你是讲故事者,{storyteller_name}。  
考虑到角色的行为,你将叙述并解释当他们采取这些行动时会发生什么,然后详细地叙述下一步应该做什么。  
以一种富有创意和吸引人的方式来叙述。不要重复已经发生的事情。  
不要改变角色!  
不要从别人的角度来说话。  
记住,你是讲故事者,{storyteller_name}。  
一旦你从你的角度说完话,就停止说话。  
切记,你的回应要控制在50字以内!  
不要添加任何其他内容。  
"""

# 角色代理的System Prompt
f"""{story_description}  
你的名字是 {character_name}。  
你的角色描述如下: {character_description}。  
你将描述你接下来要采取的具体行动,并尽量不重复任何之前的行动  
从{character_name}的角度,用{character_name}的语气来说话。  
不要改变角色!  
不要从别人的角度来说话。  
记住,你就是{character_name}。  
一旦你从你的角度说完话,就停止说话。  
千万不要忘记,你的回应要控制在{word_limit}字以内!  
不要添加任何其他内容。  
"""
  1. Agent(s) React --> Check Stroy Progression:开始进入一个循环,
    1. 随机选择的一个代理对观察到的现象做出反应。每轮循环都会随机选择一个角色代理,代理观察到是自己过往行动的和上一轮故事讲述者输出的内容,对于第一轮循环,代理观察到的是上面Prompt2生成的内容。代理用自己的System Prompt和下面给出的User Prompt1,对当前的故事作出反应。代理会把观察到的现象和自己的反应都会放入记忆库中,这里使用了LangChain的保存记忆的方法。
    2. 其他角色代理讲述者代理接收到这个反应。角色代理讲述者代理会用Prompt2把本轮抽取到的代理的反应,做成新的摘要更新自己的summary_history属性。
    3. 讲述者代理用下面Prompt3判断故事是否完结。
    4. 如果没有完成,则以讲述者代理的summary_history作为新的“观察”,开始新一轮循环。
# Prompt1
f" : {self.name} (age: {age})"  
+ f"\nInnate traits: {self.traits}"  
+ f"\n{self.summary}"
+ f"\n现在是{current_time}。"  # 当前时间, 此程序运行时间
+ f"\n{agent_name}的状态:{agent_status}"  # 当前Agent状态, 对应status属性
+ f"\n从{agent_name}的记忆中得到的相关内容摘要:"  
+ f"\n{relevant_memories}"   # 掉用LangChain的summarize_related_memories方法获取相关记忆
+ f"\n最近的观察:{most_recent_memories}"  # 没有实现
+ f"\n观察:{observation}"  # self.summary_history + 故事讲述者上一轮生成的内容
+ f"\n\n"

# Prompt2,角色代理反应。
f"""请将以下内容汇总成一个简洁的摘要,包含关键细节,包括{name}所采取的行动以及行动的结果  \n"""+
f"""{summary_history}  \n"""+ # self.summary_history属性,初始为空字符串。
f"""{name}的反应{message}  """ # 本轮抽取到的Anget反应信息

# Prompt3, 判断故事是否完结
f"""  
故事目标: {self.story_main_objective}  
目前为止的故事: {message}  
基于此"目前为止的摘要",主要的"故事目标"是否已经完成?如果获取物品是"故事目标"的一部分,物品是否已经在角色的所有物中?  
只回答"yes"或"no",不要添加任何其他内容。  
"""

  1. Storytaller Narrates Finale:用下面的Prompt输出一个结尾
f"""  
故事目标: {story_main_objective}  
最后的观察: {final_observation}  
基于这个“故事目标”和“最后的观察”,叙述一个宏大的悬念结尾。  
要富有创意和壮观!  
"""

一点思考:

  1. WhatIfGPT没有让GPT从一开始就生成整个故事,而是给出一个故事的目标,用使用若干个LangChain实现的生成式代理自己去尝试接近这么一个目标,来产生故事。代理通过不断的总结历史信息来维持记忆和保证行动的连贯性。本人虽然能感受到代理的潜力巨大非常有想象空间,但感觉目前生成的故事绝对算不上精彩,
  2. 本文忽略了项目中使用Dalle2生成角色图片,和自动生成角色语音,以及前端交互的部分。这些部分依然是非常有启发性的。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值