已阅读5页,还剩22页未读, 继续免费阅读
版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
/* 中国象棋游戏的设计与实现 关键词:中国象棋 人工智能 博弈树 Alpha-Beta 搜索 摘 要 中国象棋发展至今已有数千年的历史了,它是中华民族智慧的结晶。在我国,中国 象棋的普及程度是其它棋类无法比拟的,大至国际、国内比赛,小至社区街道。如今, 仅中国就有 2 亿人会下中国象棋,且中国象棋的发展趋势日益国际化。本文首先研究了 中国象棋在计算机中的表示问题,讨论如何产生着法等一系列相关内容,其次研究了博 弈树的搜索技术及在此基础上发展起来的相关剪枝算法。系统使用 MFC 文档视图体系 结构和 Visual C+开发工具,实现了一个具有一定棋力的中国象棋人机对弈程序。此博 弈程序实现了人机博弈,悔棋,电脑难度设置,着法名称生成等功能。 目 录 1 前言 .1 1.1 中国象棋游戏设计背景和研究意义1 1.2 国内外象棋软件发展概况1 1.3 中国象棋游戏设计研究方法1 1.4 本文的主要工作2 2 棋局表示和着法生成2 2.1 棋盘和棋子的表示2 2.2 着法生成4 3 走棋和博弈程序的实现5 3.1 博弈程序的实现5 3.1.1 搜索算法5 3.1.2 着法排序8 3.1.3 局面评估9 3.2 悔棋和还原功能的实现.11 3.3 着法名称显示功能的实现.12 3.4 胜败判定.14 4 界面设计和系统实现.15 4.1 界面设计.15 4.2 系统实现.17 5 总结.21 参 考 文 献 23 ABSTRACT 24 致 谢 25 仲恺农业工程学院毕业论文(设计)成绩评定表 26 0 1 前言 1.1 中国象棋游戏设计背景和研究意义 中国象棋游戏流传至今已经有数千年的历史了,是一种古老的文化,它集文化、科 学、艺术、竞技于一体,有利于开发人的智慧,锻炼人的思维,培养人的毅力,增强人 的竞争意识。自从计算机发明,向各个领域发展,到成为我们现在每天工作和生活必不 可少的一部分的这个过程中,电子游戏也逐步渗入我们每个人的娱乐活动中。在计算机 已经普及的今天,对于可以用计算机进行程序编辑的人来说,开发属于自己的游戏,已 经不再是梦想,中国象棋历史悠久不仅源远流长,而且基础广泛,作为一项智力运动更 成为我们游戏开发的首选对象。 中国象棋是一项智力游戏,以往都是人和人下棋,现在有了计算机我们可以和计算 机竞技,人可以与计算机进行对弈。控制计算机的是人类,而人工智能是综合性很强的 一门边缘学科,它的中心任务是研究如何使计算机去做那些过去只能靠人的智力才能做 的工作。因此,对游戏开发过程中的人工智能技术的研究自然也就成了业界的一个热门 研究方向。 1.2 国内外象棋软件发展概况 最早的象棋软件是一副可以外出携带的电子棋盘,后来升级到电视游戏机。开始出 现的一些容量很小的象棋软件如:DOS 界面将族 、WIN31 程序的中国象棋等等, 与其说人类下不过电脑,倒不如说是没有耐性等待电脑程序慢吞吞的搜索算法,有时甚 至怀疑软件是否在搜索中死掉了。后来,网络上先后出现了真正的 WINDOWS 窗口界 面的象棋专业高级软件棋隐 、 象棋世家 、 象棋参谋 、 象棋奇兵等。总而言之, 各类象棋软件既有自身的优点,也存在共通性的缺陷,如:中局审势不够智能化,走不 出弃子取势的人性化佳构,残局时智力明显低于人脑,难以走出残局例胜的必然着法等。 放眼未来,象棋软件已经走完了一波持续上涨的行情,有可能出现逐步降温的滑坡趋势。 1.3 中国象棋游戏设计研究方法 本系统主要用 Visual C+ 进行开发,里面的 MFC 类库,使游戏开发更加方便,并 利用人工智能相关搜索算法实现人工智能的着法生成,从而完善整个游戏的功能。 该象棋人机博弈系统实现的功能主要包括: 1、选手选择(人或电脑) ; 2、人机对弈(人与电脑竞技) ; 1 3、电脑棋力难度选择(电脑下棋能力难度选择,共有 4 级:按电脑配置选择难度) ; 4、悔棋、还原; 5、着法名称显示(象棋走棋规范名称) 。 1.4 本文的主要工作 第一部分主要介绍了中国象棋游戏开发的背景及意义、国内外象棋软件的发展概况 和象棋游戏的设计研究方法; 第二部分介绍了棋局表示方法和着法生成; 第三部分介绍了走棋和博弈程序的实现; 第四部分介绍了界面设计和系统的实现。 2 棋局表示和着法生成 2.1 棋盘和棋子的表示 对于中国象棋棋盘局面的表示可采用传统而简单的“棋盘数组” 。即用一个 9*10 的 数组来存储棋盘上的信息,数组的每个元素存储棋盘上是否有棋子。这种表示方法简单 易行。按此方法棋盘的初始情形如下所示: BYTE CChessBoard910 = R, 0, 0, P, 0, 0, p, 0, 0, r, H, 0, C, 0, 0, 0, 0, c, 0, h, E, 0, 0, P, 0, 0, p, 0, 0, e, A, 0, 0, 0, 0, 0, 0, 0, 0, a, K, 0, 0, P, 0, 0, p, 0, 0, k, A, 0, 0, 0, 0, 0, 0, 0, 0, a, E, 0, 0, P, 0, 0, p, 0, 0, e, H, 0, C, 0, 0, 0, 0, c, 0, h, R, 0, 0, P, 0, 0, p, 0, 0, r ; 给所有棋子定义一个值: #define R_BEGIN R_KING #define R_END R_PAWN #define B_BEGIN B_KING #define B_END B_PAWN #define NOCHESS 0 /没有棋子 2 黑方:#define B_KING 1 /黑帅 #define B_CAR 2 /黑车 #define B_HORSE 3 /黑马 #define B_CANON 4 /黑炮 #define B_BISHOP 5 /黑士 #define B_ELEPHANT 6 /黑象 #define B_PAWN 7 /黑卒 红方:#define R_KING 8 /红将 #define R_CAR 9 /红车 #define R_HORSE 10/红马 #define R_CANON 11/红炮 #define R_BISHOP 12/红士 #define R_ELEPHANT 13/红相 #define R_PAWN 14/红兵 判断颜色: #define IsBlack(x) (x=B_BEGIN if (val alpha)/保留最大值 alpha = val; return alpha; 3.1.2 着法排序 Alpha-Beta 搜索算法是在“最小-最大”的基础上引入“树的裁剪”的思想以期提高 效率,它的效率将在很大程度上取决于树的结构如果搜索了没多久就发现可以进行 “裁剪”了,那么需要分析的工作量将大大减少,效率自然也就大大提高;而如果直至 8 分析了所有的可能性之后才能做出“裁剪”操作,那此时“裁剪”也已经失去了它原有 的价值(因为你已经分析了所有情况,这时的 Alpha-Beta 搜索已和“最小-最大”搜索 别无二致了) 。因而,要想保证 Alpha-Beta 搜索算法的效率就需要调整树的结构,即调 整待搜索的结点的顺序,使得“裁剪”可以尽可能早地发生。 可以根据部分已经搜索过的结果来调整将要搜索的结点的顺序。因为,通常当一个 局面经过搜索被认为较好时,其子结点中往往有一些与它相似的局面(如个别无关紧要 的棋子位置有所不同)也是较好的。由 J.Schaeffer 所提出的“历史启发” (History Heuristic)就是建立在这样一种观点之上的。在搜索的过程中,每当发现一个好的走法, 就给该走法累加一个增量以记录其“历史得分” ,一个多次被搜索并认为是好的走法的 “历史得分”就会较高。对于即将搜索的结点,按照“历史得分”的高低对它们进行排 序,保证较好的走法(“历史得分”高的走法)排在前面,这样 Alpha-Beta 搜索就可以 尽可能早地进行“裁剪” ,从而保证了搜索的效率。 对于着法的排序可以使用各种排序算法,在程序中采用了归并排序。归并排序的空 间复杂度为 O(n),时间复杂度为 O(nlog2n),具有较高的效率。 3.1.3 局面评估 前文已经讲过了棋局表示、着法生成、搜索算法(包括搜索辅助“历史启发” ) , 在象棋程序中如果说搜索算法是心脏,那么局面评估就是大脑。搜索算法负责驱动整个 程序,而局面评估则负责对搜索的内容进行判断和评价。因而搜索与局面评估是整个下 棋引擎的核心。 首先,先介绍一下在局面评估中需要考虑的因素。就不同的棋类可能要考虑的因素 略有差异。在中国象棋中所要考虑的最基本的几个因素包括如下四点: 1、子力总和 子力是指某一棋子本身所具有的价值。通俗地讲就是一个棋子它值个什么价。例如, 车值 10 的话,那可能马值 6,卒值 2 等等。所以在评估局面时,首先要考虑双方的子力 总和的对比。比如红方拥有士象全加车马炮,而黑方只有残士象加双马,则红方明显占 优。 2、棋子位置 棋子位置,或称控制区域,是指某一方的棋子在棋盘上所占据(控制)的位置。例 如,沉底炮、过河卒、以及车占士角等都是较好的棋子位置状态,而窝心马、将离开底 线等则属较差的棋子位置状态。 9 3、棋子的机动性 棋子的机动性指棋子的灵活度(可移动性) 。例如,起始位置的车机动性较差,所 以下棋讲究早出车。同样四面被憋马腿的死马机动性也较差(对于一步也不能走的棋子, 可以认为其机动性为零) 。 4、棋子的相互关系 这一点的分析较为复杂,因为一个棋子与其它子之间往往存在多重关系。如:一个 马可能在对方的炮的攻击之下同时它又攻击着对方的车。 在程序中,估值函数最后返回的是每一方的总分的差值,而各方的总分就是上面所 提到的四个因素的打分的总和。 对于子力打分和控制区域打分,只要遍历棋盘,当遇到棋子时简单地去查事先定义 好的“子力价值表”和“控制区域价值表” ,取出相对应的值进行累加即可。 对于机动性打分,需要求出各个子总共有多少种走法,然后根据各个子所不同的机 动性价值每多一种走法就加一次相应的分数。 对棋子间相互关系的打分,要用到以下几个数据: int m_BaseValue15; /存放棋子基本价值 int m_FlexValue15; /存放棋子灵活性分值 short m_AttackPos109; /存放每一位置被威胁的信息 BYTE m_GuardPos109; /存放每一位置被保护的信息 BYTE m_FlexibilityPos109;/存放每一位置上棋子的灵活性分值 int m_chessValue109; /存放每一位置上棋子的总价值 其中计算机会进行所有棋子值的判断,AttackPos 和 GuardPos 分别记录该棋子受到 的威胁和被保护的值。 当遍历一遍棋盘之后,子力打分、控制区域打分和机动性打分都可以完成,而关系 表也可以填完。之后,再根据关系表来具体考察棋子的相互关系,进行关系打分。 分析关系时,首先,对王的攻击保护应分离出来单独考虑,因为对王的保护没有任 何意义,一旦王被吃掉整个游戏就结束了。 其次,对一个普通子,当它既受到攻击又受到保护的时候要注意如下几个问题: 1、攻击者子力小于被攻击者子力,攻击方将愿意换子。比如,一个车正遭受一个 炮的攻击,那么任何对车的保护都将失去意义对方肯定乐意用一个炮来换一个车。 2、多攻击/单保护的情况,并且攻击者最小子力小于被攻击者子力与保护者子力之 10 和,则攻击方可能以一子换两子。 3、三攻击/两保护的情况,并且攻击者子力较小的二者之和小于被攻击者子力与保 护者子力之和,则攻击方可能以两子换三子。 4、攻击方与保护方数量相同,并且攻击者子力小于被攻击者子力与保护者子力之 和再减去保护者中最大子力,则攻击方可能以 n 子换 n 子。 当然,上述四条只是覆盖了最常见的几种情况,覆盖并不全面。而且,在程序中并 没有直接地重新考虑双方兑子之后的控制区域及机动性变化情况(之所以说没有“直接 地重新考虑” ,是因为搜索继续展开结点后仍会考虑这些因素,只是目前不知这样效果 是否受影响考察这两种方法在效果上的差异需要一定数量的试验数据的支持) 。所 以,如果今后要对引擎进行改进,提高程序的下棋水平的话,还应当在此进行研究。 3.2 悔棋和还原功能的实现 悔棋和还原是棋类软件中较为基本的功能。要实现悔棋和还原功能,首先要明确哪 些信息应当被保存以供悔棋和还原所使用。 在程序中保存了如下信息: 棋局表示中所定义的棋盘数组; 各棋子的贴图位置; 这里需要特别说明的是通常象棋程序处于程序效率的考虑并不保存所有棋子的信息, 而只是保存之前一步的走棋信息。此后当悔棋的时候,需要撤销着法;还原的时候,需 要执行着法。然而,在编写自己的程序时一来考虑到程序的可读性和不易出错性,二来 考虑到对当今的计算机的配置来说这点开销基本上不会对程序的效率产生什么影响。因 此保存了全部棋子的信息。 根据所要保存的数据定义了如下基本结构类型: typedef struct CHESSMOVE cmChessMove; short nChessID;/被吃掉的棋子 UNDOMOVE; 在对弈过程中,每一回合都将棋局信息(这里指前面所说的需要保存的信息)保存 至走法队列,以供悔棋所用。还原功能是与悔棋功能相对应的,只有当产生了悔棋功能 之后,还原功能才会被激活。一个回合的结束意味着前一次操作没有悔棋功能的产生, 因此还原队列也应被清空。 11 在悔棋中主要完成了以下任务: 1、下棋回合数减一; 2、将当前局面信息保存至走法队列,以供还原所用; 3、从走法队列中取出上一回合的棋局信息,恢复到当前局面,然后将其从 队列中剔除掉; 4、将显示着法名称的列表框中的本回合的着法名称保存到一个着法名称队 列,以供还原所用。然后从列表框中删除它。 而在还原中所做的刚好和悔棋相反: 1、下棋回合数加一; 2、将当前局面信息保存至队列,以供悔棋所用; 3、从队列中取出最近一次悔棋前的棋局信息,恢复到当前局面,然后将其从队列 中剔除; 4、从走法队列中取出最近一次存入的着法名称(两项,因为每回合会产生两步着 法) ,将其重新显示到列表框中。然后将其从中剔除。 以上便是悔棋和还原功能所完成的具体操作,其代码分别写入悔棋和还原按钮 (Button)的事件处理函数中。 3.3 着法名称显示功能的实现 每当下棋者(用户或是计算机)走一步棋,在棋盘旁边的一个列表框控件(List Box)中按照中国象棋关于着法描述的规范要求显示出该着法的名称。如:炮八进四、 马二进三此类。为了获得该着法名称,我们编写了一个函数,其功能就是将被移动的棋 子类型以及走法的起点坐标、终点坐标这些信息转换成中国象棋所规范的着法名称。实 现此功能代码如下: void CGradientProgressCtrl:OnPaint() CPaintDC dc(this); / device context for painting / TODO: Add your message handler code here if(m_nCurrentPosition=m_nUpper) CRect rect; GetClientRect(rect); CBrush brush; 12 brush.CreateSolidBrush(:GetSysColor(COLOR_3DFACE); dc.FillRect( VERIFY(brush.DeleteObject(); return; CRect rectClient; GetClientRect(rectClient); float maxWidth(float)m_nCurrentPosition/(float)m_nUpper*(float)rectClient.right); /绘制 DrawGradient( /显示进程条进度文字 if(m_bShowPercent) CString percent; percent.Format(“%d%“,(int)(100*(float)m_nCurrentPosition/m_nUpper); dc.SetTextColor(m_clrText); dc.SetBkMode(TRANSPARENT); dc.DrawText(percent, /显示其他文字 if(m_bIsShowText) dc.SetTextColor(m_clrText); dc.SetBkMode(TRANSPARENT); dc.DrawText(m_strShow, / Do not call CProgressCtrl:OnPaint() for painting messages int CGradientProgressCtrl:SetPos(int nPos) /Set the Position of the Progress m_nCurrentPosition=nPos; return (CProgressCtrl:SetPos(nPos); 13 int CGradientProgressCtrl:StepIt() m_nCurrentPosition+=m_nStep; return CProgressCtrl:StepIt(); 以下介绍如何对列表框控件(List Box)进行操作,以显示或删除着法名称。 首先,在 ChessDlg 下定义以下函数: this-GetMoveStr(nFromX,nFromY,nToX,nToY,nSourceID); /用来获得刚下的一步棋的走法; void CChessDlg:AddChessRecord(int nFromX,int nFromY,int nToX,int nToY,int nUserChessColor,int nSourceID) /将走法添加进下棋记录; 然后,显示在 Listbox 中。 当列表框中的项的数目超过列表框的显示范围时,列表框会自动添加垂直滚动条 (前提是其 VerticalScrollbar 属性要为 True该属性默认即为 True) 。但是显示的内容 依然是最早加进来的项。在控件属性里选择 Vertical Scroll,使得列表框可垂直滚动以 显示最新的着法名称。 想要从列表框中删除项时,可以使用 m_lstChessRecord.DeleteString(m_lstChessRecord.GetCount()-1);减一之后正好是最后 一项的行号。 3.4 胜败判定 胜负判定只要一方将另一方的将或帅吃掉就是胜者。 主要代码如下: int CSearchEngine:IsGameOver(BYTE position9, int nDepth) int i,j; BOOL RedLive=FALSE,BlackLive=FALSE; /检查红方九宫是否有帅 for(i=7;i10;i+) for(j=3;j6;j+) 14 if(positionij=B_KING) BlackLive=TRUE; if(positionij=R_KING) RedLive=TRUE; /检查黑方九宫是否有将 for(i=0;i3;i+) for(j=3;j6;j+) if(positionij=B_KING) BlackLive=TRUE; if(positionij=R_KING) RedLive=TRUE; i=(m_nMaxDepth-nDepth+1)%2;/取当前奇偶标志,奇数层为电脑方,偶数层为用户 方。 /红方不在 if(!RedLive) if(i) return 19990+nDepth; /奇数层返回极大值 else return -19990-nDepth;/偶数层返回极小值 /黑方不在 if(!BlackLive) if(i) return -19990-nDepth;/奇数层返回极小值 else return 19990+nDepth; /偶数层返回极大值 return 0;/将帅都在,返回 0 15 4 界面设计和系统实现 4.1 界面设计 关于棋盘和棋子,建了一个基于对话框的 MFC 应用程序。主要工作都在对话框类 的两个文件 CChessDlg.h 和 CChessDlg.cpp 下展开。 代码主要分布于以下三大部分: 1、初始化部分 BOOL CCChessUIDlg:OnInitDialog() OnInitDialog()负责的是对话框的初始化。可以把有关中国象棋的棋局初始化情况也 放在了这里面。初始化的内容包括: 对引擎部分所用到的变量的初始化。包括对棋盘上的棋子位置进行初始化(棋盘数 组的初始化) ,对搜索深度、当前走棋方标志、棋局是否结束标志等的初始化; 对棋盘、棋子的贴图位置(即棋盘、棋子在程序中实际显示位置)的初始化; 对程序辅助部分所用到的一些变量的初始化。包括对悔棋、还原队列的清空,棋盘、 棋子样式的默认形式,下棋模式的默认选择,以及着法名称列表的初始化等。 2、绘图部分 void CCChessUIDlg:OnPaint() OnPaint()函数负责的是程序界面的绘图。因此,在这里将要完成棋盘、棋子的显示 走棋起始位置和目标位置的提示框的显示。 由于棋盘、棋子等都是以位图的形式给出的。所以在 OnPaint()函数里做的工作主要 都是在贴位图。 需要注意的是由于位图文件不能像 GIF 文件那样有透明的背景并且棋子是圆形的而 位图文件只能是矩形的,所以如果直接贴图的话会在棋盘上留下一块白色的边框棋 子的背景。因此,要想让棋子文件的背景“隐藏”需要通过一些“与”和“异或”操作 来屏蔽掉棋子的背景。 3、走棋部分(用户动作响应部分) 为 WM_LBUTTONDOWN 消息添加消息响应事件,可得到如下函数: 16 void CCChessUIDlg:OnLButtonDown(UINT nFlags, CPoint point) 当用户在窗口客户区按下鼠标左键时,程序就会调用 OnLButtonDown(UINT nFlags, CPoint point)函数来进行响应。其中第二个参数 CPoint point 是在本程序中所要用到的, 它给出了当鼠标左键被按下时,鼠标指针的位置坐标。可以通过这一信息来得知用户的 走法。 在 OnLButtonDown 函数里处理如下两种操作: 1、如果用户点击鼠标的位置落在己方的棋子上,表示用户选中了该棋子,下一步 将移动该子进行走棋(也可能用户下一步将会选择己方另外的棋子,总之这一操作会记 录下用户所选的将要走的棋子) 。 2、如果之前用户已经选过了棋子,那么这一次的点击(如果不是另选本方的其它 棋子的话)表达了用户的一次走棋过程。在收到用户传达的走棋信息后,可先判断该着 法是否合法(是否符合中国象棋的游戏规则) ,如果合法,则执行之。紧接着调用引擎 的搜索函数计算出计算机对用户着法的应着,然后执行该应着。 如此,在 OnLButtonDown 函数里,实现了人与机器的对弈(当然每走一步棋,也 还需要绘图函数来显示棋盘局面的更新) 。 以上三部分并非界面程序的全部,而仅仅是与程序密切相关的部分。此外还有其它 部分对程序同样必不可少,但这些部分主要由 MFC 自动生成,无需人为改动,故在此 不多做介绍。 4.2 系统实现 现在已具备了实现一款中国象棋对弈程序引擎部分的所有要素,将上述模块分别写 作.h 头文件。如下: ChessDlg.h 象棋相关定义。包括棋盘局面和着法的表示。 BaseClasses.h 着法生成器。就当前局面生成某一方所有合法着法。 MoveList.h 搜索部分。使用搜索求出最佳着法。 Thinkdef.h 17 历史启发。Alpha-Beta 搜索之补充,以提高搜索效率。 Thinker.h 着法排序。对着法按其历史得分进行降序排序,以提高搜索效率。 ThinkOptionDlg.h 局面评估。为某一特定局面进行评分。 当实现了引擎部分的各要素时,可先建立一个 Win32 控制台项目,之后只要再添加 一个.cpp 文件负责接受用户的输入、调用搜索函数、显示搜索结果,便可简单的测试引 擎了(采用输入着法的起点坐标和终点坐标的方式来传送用户走棋的信息。同样,程序 显示计算机走棋的起点坐标和终点坐标来做出回应) 。 此后,等到界面部分初步完成,引擎的上述各模块无需作任何改动,仍以.h 头文件的形 式加入界面工程,只要由界面中的某个.cpp 文件调用搜索函数即可。这种连接方式实现 起来非常简单。 首先,执行该软件,系统并不需要很高的配置,CPU 在 1.5G 以上,内存在 512M 以上就可以很流畅地执行。下面简单介绍一下象棋相关规则: 对局时,由执红棋的一方先走,双方轮流各走一着,直至分出胜、负、和,对局即 终了。轮到走棋的一方,将某个棋子从一个交叉点走到另一个交叉点,或者吃掉对方的 棋子而占领其交叉点,都算走一着。双方各走一着,称为一个回合。如果有一方的主帅 被对方吃了,就算那一方输。 各种棋子的走法: 帅(将):帅和将是棋中的首脑,是双方竭力争夺的目标。它只能在“九宫”之内 活动,可上可下,可左可右,每次走动只能按竖线或横线走动一格。帅与将不能在同一 直线上直接对面,否则走方判负。 仕(士):仕(士)是帅(将)的贴身保镖,它也只能在九宫内走动。它的行棋路 径只能是九宫内的斜线。 相(象):相(象)的主要作用是防守,保护自己的帅(将) 。它的走法是每次循 对角线走两格,俗称“象走田” 。相(象)的活动范围限于“河界”以内的本方阵地, 不能过河,且如果它走的“田”字中央有一个棋子,就不能走,俗称“塞象眼” 。 车:车在象棋中威力最大,无论横线、竖线均可行走,只要无子阻拦,步数不受 限制。因此,一车可以控制十七个点,故有“一车十子寒”之称。 炮:炮在不吃子的时候,走动与车完全相同。 18 马:马走动的方法是一直一斜,即先横着或直着走一格,然后再斜着走一个对角线, 俗称“马走日” 。马一次可走的选择点可以达到四周的八个点,故有“八面威风”之说。 如果在要去的方向有别的棋子挡住,马就无法走过去,俗称“蹩马腿” 。 兵(卒):兵(卒)在未过河前,只能向前一步步走,过河以后,除不能后退外, 允许左右移动,但也只能一次一步。 在懂的以上规则之后并可进行游戏,执行该软件后,并可进入游戏界面。棋盘界面 (图 3)所示: 图 3 棋盘界面 从界面上方的菜单栏中可以进行相关设置 参数设置界面(图 4)如下: 19 图 4 参数设置界面 等你将参数设置完毕之后,既可进入游戏。走法记录界面(图 5)如下: 图 5 走法记录界面 其他辅助功能界面(图 6)如下: 图 6 其他辅助功能界面 你可以通过上面四个辅助功能对棋局进行研究,从而提高你的下棋水平。 例如,您是红方,第一步走的是兵七进一或兵三进一,电脑则会炮 2 进 4 或炮 8 进 4(图 7): 20 图 7 程序运行界面 以上是系统实现的所有界面及功能测试。 5 总结 2009 年 2 月,我开始了我的毕业论文工作,时至今日,论文基本完成。从最初的茫 然,到慢慢的进入状态,再到对思路逐渐的清晰,整个写作过程难以用语言来表达。历 经了几个月的奋战,紧张而又充实的毕业设计终于落下了帷幕。回想这段日子的经历和 感受,我感慨万千,在这次毕业设计的过程中,我拥有了无数难忘的回忆和收获。 脚踏实地,认真严谨,实事求是的学习态度,不怕困难、坚持不懈、吃苦耐劳的精 神是我在这次设计中最大的收益。我想这是一次意志的磨练,是对我实际能力的一次提 升,也会对我未来的学习和工作有很大的帮助。 在这次毕业设计中也使我们的同学关系更进一步了,同学之间互相帮助,有什么不懂的 大家在一起商量,听听不同的看法对我们更好的理解知识,所以在这里非常感谢帮助我 的同学。 在此更要感谢我的导师和专业老师,是你们的细心指导和关怀,使我能够顺利的完 成毕业论文。在我的学业和论文的研究工作中无不倾注着老师们辛勤的汗水和心血。老 21 师的严谨治学态度、渊博的知识、无私的奉献精神使我深受启迪。从尊敬的导师身上, 我不仅学到了扎实、宽广的专业知识,也学到了做人的道理。在此我要向我的导师致以 最衷心的感谢和深深的敬意。 本论文对计算机博弈技术进行了研究,在深入研究了机器下中国象棋方法理论基础 上,实现了一个具有一定棋力的人机对弈中国象棋程序。然而,由于时间关系,程序也 存在着几点不足: 第一:没对计算机下棋引擎部分作更深一步的挖掘和研究。对于诸如位棋盘 (BitBoard) 、迭代加深(Iterative Deepening) 、机器学习(Machine Learning)等当今棋 类对弈程序中所采用的先进技术和思想,在程序中并未涉及。这在一定程度上影响了程 序中下棋引擎的工作效率。 第二:由于对人工智能算法的不熟悉,在 Alpha-Beta 搜索算法上花了大量的时间和 精力来了解,导致程序进度的缓慢。 尽管,这些问题最终都得以解决,但却影响了程序开发的进程。 第三、程序仍在局面检测和贴图刷新上存在着随机性的出错可能(出错几率很小) 。 22 参 考 文 献 1 王小春.PC 游戏编程(人机博弈)M. 重庆:重庆大学出版社,2002. 2 网冠科技.Visual C+.NET 小游戏开发时尚编程百例M .西安:机械工业出版社,2004. 3 陈建春.Visual C+ 高级编程技术开发实例剖析M.西安:电子工业出版社,1999. 4 涂光平等.Visual C+.NET 基础教程与上机指导M.北京:清华大学出版社,2005. 5 伍红兵.Visual C+ 编程深入引导 M.长春:中国水利水电出版社,2002. 6 Frederic Friedel.电脑国际象棋简史EB/OL. auntyellow/computer/history.htm,2007-3-7。 7 Franois Dominic Larame.国际象棋程序设计(一):引言EB/OL.http:/homepage. 8 Fr
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 宁德市蕉城区南埕学校幼儿园招聘编外人员考试备考题库及答案详解
- 2026年竹山县中小学幼儿园教师招聘考试参考题库及答案解析
- 2025年专升本黑龙江英语真题及答案
- 2025 社区卫生服务中心内部管理制度
- 2026年顺昌县中小学幼儿园教师招聘考试备考试题及答案解析
- 2026中国通信设备运营商行业市场供需分析及投资评估规划分析研究报告
- 2026南平建阳法院招聘速录员2名笔试备考试题及答案详解
- 2026安徽省人力资源有限公司招聘驻点国有企业新媒体编辑岗1人笔试参考题库及答案详解
- 2026年抚顺县中小学幼儿园教师招聘笔试备考题库及答案解析
- 2026年福建省酒业股份有限公司招聘3人笔试模拟试题及答案详解
- 2026-2030中国大型锻件市场应用规模及需求前景分析研究报告
- 公共综合廊道工程社会稳定风险评估报告
- 2026日本智能手机行业市场现状供需调研及投资前景规划分析报告
- 2026年秋季湘教版(新版)九年级上册数学教学计划及进度表
- 湖北省荆州市监利市2025-2026学年七年级下学期6月期末数学试题(含答案)
- 小学生爱国主义教育与使命担当小学主题班会课件
- 2026年湖北省中考历史试卷(含答案)
- 2026年小学二年级升三年级语文暑假衔接作业(完整版)
- 机械类就业指导研究
- 天津天津东疆综合保税区管理委员会面向社会招聘笔试历年参考题库附带答案详解(5卷)
- 2026安徽省供销集团有限公司集团本部纪检工作人员招聘3人考试备考试题及答案解析
评论
0/150
提交评论