3. 博弈树 (15分)

news2024/11/14 17:40:32

下棋属于一种博弈游戏,博弈过程可以用树(博弈树)来表示。假设游戏由两个人( A 和 B )玩,开始由某个人从根结点开始走,两个人轮流走棋,每次只能走一步, 下一步棋只能选择当前结点的孩子结点,谁先走到叶子结点为胜。例如,对于下图所示的博弈树,若 A 先走,可以选 f , B 若选 h ,则 A 选 j 胜。

编写一程序,让计算机和人下棋。当计算机走下一步时,可以根据以下情况决定下一步:

(1) 若存在可以确保取胜的一个孩子结点,则选择该结点作为下一步;

(2) 若存在多个可以确保取胜的孩子结点,则选择其中高度最小的结点作为下一步(若有多个选择,则选最左边的结点);

(3) 若不存在可以确保取胜的一个孩子结点,则选择高度最大的孩子结点作为下一步(若有多个选择,则选最左边的结点);

例: (下面的黑体为输入)

(a,(b,(x)),(c,(d),(e,(g),(h)),(f)))

a

b

x

c

d

e

g

h

f

Who play first(0: computer; 1: player )?

1

player:

c

computer: d

Sorry, you lost.

Continue(y/n)?

y

Who play first(0: computer; 1: player )?

1

player:

x

illegal move.

player:

b

computer: x

Sorry, you lost.

Continue(y/n)?

y

Who play first(0: computer; 1: player )?

0

computer: c

player:

f

Congratulate, you win.

Continue(y/n)?

n

测试输入期待的输出时间限制内存限制额外进程
测试用例 1以文本方式显示
  1. (a,(b,(x)),(c,(d),(e,(g),(h)),(f)))↵
  2. 1↵
  3. c↵
  4. y↵
  5. 1↵
  6. x↵
  7. b↵
  8. y↵
  9. 0↵
  10. f↵
  11. n↵
以文本方式显示
  1. a↵
  2. b↵
  3. x↵
  4. c↵
  5. d↵
  6. e↵
  7. g↵
  8. h↵
  9. f↵
  10. Who play first(0: computer; 1: player )?↵
  11. player:↵
  12. computer: d↵
  13. Sorry, you lost.↵
  14. Continue(y/n)?↵
  15. Who play first(0: computer; 1: player )?↵
  16. player:↵
  17. illegal move.↵
  18. player:↵
  19. computer: x↵
  20. Sorry, you lost.↵
  21. Continue(y/n)?↵
  22. Who play first(0: computer; 1: player )?↵
  23. computer: c↵
  24. player:↵
  25. Congratulate, you win.↵
  26. Continue(y/n)?↵
1秒64M0
测试用例 2以文本方式显示
  1. (a,(b,(c,(d),(e)),(f)),(g,(h),(i)),(j,(k,(m),(n),(o),(p,(r))),(x,(y,(z)))))↵
  2. 1↵
  3. j↵
  4. y↵
  5. y↵
  6. 1↵
  7. b↵
  8. y↵
  9. 0↵
  10. k↵
  11. n↵
以文本方式显示
  1. a↵
  2. b↵
  3. c↵
  4. d↵
  5. e↵
  6. f↵
  7. g↵
  8. h↵
  9. i↵
  10. j↵
  11. k↵
  12. m↵
  13. n↵
  14. o↵
  15. p↵
  16. r↵
  17. x↵
  18. y↵
  19. z↵
  20. Who play first(0: computer; 1: player )?↵
  21. player:↵
  22. computer: x↵
  23. player:↵
  24. computer: z↵
  25. Sorry, you lost.↵
  26. Continue(y/n)?↵
  27. Who play first(0: computer; 1: player )?↵
  28. player:↵
  29. computer: f↵
  30. Sorry, you lost.↵
  31. Continue(y/n)?↵
  32. Who play first(0: computer; 1: player )?↵
  33. computer: j↵
  34. player:↵
  35. computer: m↵
  36. Sorry, you lost.↵
  37. Continue(y/n)?↵
1秒64M0
测试用例 3以文本方式显示
  1. (a,(b,(c,(d),(e)),(f)),(g,(h),(i)),(q,(k,(m),(n),(o),(p,(r))),(x,(y,(z)))))↵
  2. 1↵
  3. q↵
  4. x↵
  5. y↵
  6. n↵
以文本方式显示
  1. a↵
  2. b↵
  3. c↵
  4. d↵
  5. e↵
  6. f↵
  7. g↵
  8. h↵
  9. i↵
  10. q↵
  11. k↵
  12. m↵
  13. n↵
  14. o↵
  15. p↵
  16. r↵
  17. x↵
  18. y↵
  19. z↵
  20. Who play first(0: computer; 1: player )?↵
  21. player:↵
  22. computer: x↵
  23. player:↵
  24. illegal move.↵
  25. player:↵
  26. computer: z↵
  27. Sorry, you lost.↵
  28. Continue(y/n)?↵
1秒64M0

博弈树学习笔记:

完全博弈问题--下棋

特点:

    双人对弈: 轮流下,一人走一步.

    信息完备: 双方看到的信息一样.

    零和: 双方利益冲突,对一方有利则对另一方不利。

极小极大搜索方法: (假定对手每次回应都正确,即选择MIN)

    假定有一个评价函数可以对所有的棋局进行评估.

    评价函数值大于0,棋局对我方有利,对对方不利,反之同理.

    对节点N取估价函数f(N),分两类节点:

        Max,有选择时取最大;

        Min,有选择时取最小.

具体思路:

    1.我方走棋时,首先按照一定的搜索深度生成出给定深度d以内的所有状态,计算所有叶节点的评价函数值, 然后从d-1层节点开始逆向计算.

    2.对于我方要走的节点(MAX),取其子节点中的最大值为该节点的值(选择对我方有利的棋)。

    3.对于对方要走的节点(MIN),取其子节点中的最小值为该节点的值(选择对我方不利的棋)。

    4.直到计算出根节点的值为止,获得根节点取值的分枝即为最佳选择.

    5.对方回应一步棋后,重新演算.

显然这样做太低效了,需要剪枝,分析:

α-β搜索方法定义:(其实就是给节点定义范围区间--[α,β],初始化为+-∞)

    Max节点的下界为α,Min节点的上界为β.

    极大节点N,从一个子树获得的α值和β值,可以传送给其他子节点

    极大节点N的α值只可能越改越大,极小节点M的β值只可能越改越小.

    从单边子节点往父节点推,极大值父节点只更改α值,极小值父节点只更改β值.

α剪枝(发生在极小层节点)---从一个子树获得的极大节点的α值,可以传送给该节点的其他子树,从而选择α剪枝机会

    若对任一极小值层节点,α(任意父辈层)≥β(后继层),则可中止此MIN节点以下的搜索过程.

    此MIN节点的最终倒推值就确定为此β值.

β剪枝(发生在极大层节点)---从一个子树获得的极小节点的β值,可以传送给该节点的其他子节点,从而选择β剪枝机会

    若对任一极大值层节点,α(后继层)≥β(任意父辈层),则可中止此MAX节点以下的搜索过程.

    此MAX节点的最终倒推值就确定为此α值。

代码(先给个头文件混混,等我明天再改改,我觉得写的还是不够好,没剪枝)

        吐槽:晚上写完感觉逻辑没问题终于交了,结果还是WA,后来发现是输出少了空格(这一句:Who play first(0: computer; 1: player )?);改了之后AC了,,,但是看了看报表,看到一个1378B,22行过的,于是我看着我9492B,391行的代码陷入了沉思(嘶,不是哥们,这我怎么睡的着啊?就22行,我是真想不明白,除了printf/cout还能怎么写,毕竟这次测试用例是给出的三个,没有隐藏)

#include <iostream>
#include <string>
#include <algorithm>
using namespace std;

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1135107.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Python 算法高级篇:启发式搜索与 A *算法

Python 算法高级篇&#xff1a;启发式搜索与 A *算法 引言 1. 什么是启发式搜索&#xff1f;1.1 启发式函数的特性1.2 启发式搜索算法 2. A *算法的原理2.1 A *算法的伪代码2.2 A *算法的优点 3. Python 中的 A *算法实现4. 总结 引言 启发式搜索是一种常用于解决路径规划和优…

【Java集合类面试二十九】、说一说HashSet的底层结构

文章底部有个人公众号&#xff1a;热爱技术的小郑。主要分享开发知识、学习资料、毕业设计指导等。有兴趣的可以关注一下。为何分享&#xff1f; 踩过的坑没必要让别人在再踩&#xff0c;自己复盘也能加深记忆。利己利人、所谓双赢。 面试官&#xff1a;说一说HashSet的底层结构…

【CCF-A类】IEEE-TRANS系列,1区顶刊,WOS稳定收录32年,对国人友好,仅17天检索!

论文写作堪比西天取经&#xff0c;当我们经历“九九八十一难&#xff0c;取得真经“&#xff0c;还有最关键的一步&#xff0c;就是选刊发表。是“投石问路”&#xff0c;还是“投其所好”&#xff1f; 选刊有多重要&#xff0c;相信只要有过发表SCI经验的人都十分清楚。如果不…

【QT】对象树

一、QT对象树的概念 先来看一下 QObject 的构造函数&#xff1a; 通过帮助文档我们可以看到&#xff0c;QObject 的构造函数中会传入一个 Parent 父对象指针&#xff0c;children() 函数返回 QObjectList。即每一个 QObject 对象有且仅有一个父对象&#xff0c;但可以有很多个…

什么是间谍软件恶意软件?

攻击者利用此类软件从受感染的设备中收集和传输信息。这可能包括个人、银行和用户凭证&#xff08;社交网络、流媒体服务、邮件等的登录名和密码&#xff09;&#xff0c;以及设备内存中的文件。 在间谍软件的帮助下&#xff0c;欺诈者还可以窃取公司凭证&#xff0c;不仅伤害…

Vue 3中toRaw和markRaw的使用

文章目录 Vue 3的响应性系统使用toRaw使用markRaw使用场景1. 与第三方库交互2. 提高性能3. 避免无限循环 总结 &#x1f389;欢迎来到Java学习路线专栏~探索Java中的静态变量与实例变量 ☆* o(≧▽≦)o *☆嗨~我是IT陈寒&#x1f379;✨博客主页&#xff1a;IT陈寒的博客&#…

Linux基础:2:shell外壳+文件权限

shell外壳文件权限 一.shell原理&#xff1a;1.对比&#xff1a;windo GUI 和 shell1.windo GUI2. shell 2.为什么&#xff1f;是什么&#xff1f;怎么办&#xff1f;1.为什么有shell2.是什么&#xff1f;3.怎么办&#xff1f;4.补充&#xff1a; 二.linux权限管理&#xff1a;…

Linux redis 安装

1、解压 tar -zxvf redis-5.0.10.tar.gz 2、cd /data/redis-5.0.10 文件夹 3、make 等待make命令执行完成即可。 make命令报错&#xff1a;cc 未找到命令&#xff0c;系统中缺少gcc&#xff0c;执行命令安装 gcc&#xff1a; yum -y install gcc automake autocon…

蓝桥杯每日一题2023.10.25

乘积尾零 - 蓝桥云课 (lanqiao.cn) 题目描述 题目分析 由于需要相乘的数很多&#xff0c;所以我们不能直接进行暴力模拟&#xff0c;我们知道10 2 * 5&#xff0c; 所以我们只需要找出这个数2和5的个数&#xff0c;其中2和5个数小的那个则为末尾0出现的个数 #include<bi…

探讨安科瑞低压备自投装置AM5-DB的应用-安科瑞 蒋静

1 概况 本项目主要为发电机组供电切换提供备自投保护功能&#xff0c;该发电机组的供电主要由两进线一母联的系统组成&#xff0c;其中&#xff0c;每路进线分别由一路市电和一路柴油发电机切换提供&#xff0c;故此&#xff0c;我司用了三台低压备自投装置AM5-DB来实现备自投…

软信天成:助力某制造企业建设产品主数据管理平台案例分享

某国有大型传统制造企业是一家跨领域、跨行业经营的国际化公司&#xff0c;在全球范围内拥有动力系统、工程机械、汽车制造等多个业务板块、分子公司遍及世界、产品远销110多个国家和地区&#xff0c;产品品类繁多&#xff0c;分支架构错综复杂。 近年来&#xff0c;数字化的深…

欢迎浪潮KaiwuDB成为开源社白金合作伙伴

众多开源爱好者翘首期盼的开源盛会&#xff1a;第八届中国开源年会&#xff08;COSCon23&#xff09;将于 10月28-29日在四川成都市高新区菁蓉汇举办。本次大会的主题是&#xff1a;“开源&#xff1a;川流不息、山海相映”&#xff01;各位新老朋友们&#xff0c;欢迎到成都&a…

Find My护照|苹果Find My技术与护照结合,智能防丢,全球定位

护照是一个国家的公民出入本国国境和到国外旅行或居留时&#xff0c; 由本国发给的一种证明该公民国籍和身份的合法证件。 护照&#xff08;PASSPORT&#xff09;一词在英文中是口岸通行证的意思。也就是说&#xff0c; 护照是公民旅行通过各国国际口岸的一种通行证明。 护照…

非对称加密---椭圆曲线---单向散列函数

4. 非对称加密 "非对称加密也叫公钥密码: 使用公钥加密, 使用私钥解密"在对称密码中&#xff0c;由于加密和解密的密钥是相同的&#xff0c;因此必须向接收者配送密钥。用于解密的密钥必须被配送给接收者&#xff0c;这一问题称为密钥配送问题。如果使用非对称加密也…

C语言求数组最小值,并返回下标

#include<stdio.h> #include<string.h> void main() {int a[] {12,5,21,33,55,77,11,2};int zf sizeof(a) / sizeof(a[0]);for (int i 0; i < zf; i){if (a[i] < a[0]){a[0] a[i];}}printf("最小为%d&#xff0c;下标是0",a[0]); } 如果是求最…

markdown操作

一、语法设置 1.1 标题 1.1.1 使用’#表示标题 #必须在行首&#xff0c;#越多&#xff0c;标题的级别越低1.2 代码块 1.2.1 行内代码块 使用反单引号&#xff08;一般在键盘的左上位置&#xff0c;和~是一个键&#xff09;来表示&#xff0c;如 hello&#xff1a;hello 1.2…

Windows一些基础设置

开机自启动 方法一&#xff1a; 1、首先按下键盘上的“Wini”打开设置窗口&#xff0c;在左边找到并进入“应用”&#xff1b; 2、接着在右侧点击并进入“启动”设置。 3、在启动应用下&#xff0c;将不需要开机自启动的软件给关掉。 方法二&#xff1a; 1、按CtrlShiftEs…

使用HXT和Haskell编写的程序

以下是一个使用HXT和Haskell编写的下载器程序&#xff0c;用于下载内容。此程序使用了proxy的代码。 -- 导入必要的库 import Network.HTTP.Conduit import Network.HTTP.Types.Status import Network.HTTP.Types.Header import Data.Conduit import Data.Conduit.Network imp…

Python 算法高级篇:布谷鸟哈希算法与分布式哈希表

Python 算法高级篇&#xff1a;布谷鸟哈希算法与分布式哈希表 引言 1. 什么是哈希算法&#xff1f;1.1 哈希算法的用途 2. 布谷鸟哈希算法2.1 布谷鸟哈希表的特点2.2 布谷鸟哈希算法的伪代码2.3 Python 中的布谷鸟哈希算法实现 3. 分布式哈希表3.1 分布式哈希表的特点3.2 一致性…

为啥外行都觉得程序员的代码不值钱?

点击下方“JavaEdge”&#xff0c;选择“设为星标” 第一时间关注技术干货&#xff01; 免责声明~ 任何文章不要过度深思&#xff01; 万事万物都经不起审视&#xff0c;因为世上没有同样的成长环境&#xff0c;也没有同样的认知水平&#xff0c;更「没有适用于所有人的解决方案…