趣味数学游戏五子棋

2022-08-22

第一篇:趣味数学游戏五子棋

小学数学趣味教学:扑克牌玩24点玩算术游戏

昨日上午9时,北部新区童心小学四年级1班教室里,一堂数学课正在进行。不过,孩子们没有端正坐好听老师讲课,却三三两两玩起了扑克牌,你一张我一张出得很欢快,不时还传来我的牌最多,我赢了的欢呼声。

小学生在课堂上玩扑克牌?其实,他们是在用扑克牌玩24点算术游戏,这也是数学老师张先彬教学方法里重要的一部分。

比练习综合算术好玩多了

上课前,张先彬先把3副扑克牌分发到了班上的12位同学手中,然后问了一个与课堂似乎不太相干的问题:扑克牌,大家都听说过哪些玩法?问题一出,课堂上突然活跃了起来,我知道干瞪眼!我知道斗地主!我知道升级!

张先彬将班上12位同学分成3组,每4个人拿一副扑克牌。一副牌去掉大小王之后,还剩52张,除了数字牌外,J、Q、K都代表数字10,A代表数字1,每人手上13张牌。每一局游戏中,每位同学出一张牌,同一组的4位同学用这4张牌分别代表的数字思考算法,谁最先想出结果是24的算法,谁就获得这4张牌,最后谁手中牌最多谁就赢。

童心小学是所新学校,本学期刚开课,四年级1班的同学都是从其它学校转学来的,所以只有12个人。张先彬说:24点其实人多更好玩,会有更多的题目和解法。

同学向星樾告诉重庆晚报记者,以前她不是特别喜欢做计算题,但是却很喜欢张老师的24点算术游戏,比练习综合算术好玩多了,一点都感觉不到算术的烦心。星樾妈妈认为,这样的数学课增加了趣味性,让孩子在快乐中学习,对成长非常有帮助。

24点算术游戏有17份教案

数学课结束后,张先彬告诉重庆晚报记者,看似简单的24点算术游戏,他一共就准备了17份教案,这些教案从简单到复杂,蕴含着小学数学加减乘除四则运算的学习过程。

张先彬介绍说,17份教案就是17个课时,二年级开始学第1课时,随着运算学习的递进,到四年级时就可以学到后面的课时。也就是说,24点算术游戏课将穿插到二年级至四年级加减乘除运算学习的整个过程中,适时提高孩子的运算兴趣。

当然,平时的教学都是按照教学大纲进行,但是用什么样的方法进行教学,为孩子带来收获,我有自己的设计,24点游戏事实上就是四则运算的教学内容之一。张先彬说,在其它我任教的班上,二年级、三年级也将陆续用上这套教案。

北部新区童心小学校长秦波告诉记者,该校的教学理念是保护儿童的童真和天性,让他们在快乐中成长,所以老师们的教学方式都由自己决定,学校不做硬性安排。张先彬老师在这样的教学理念下,可以自由施展自己的教学才华。

这位数学老师还有很多招数

除了将24点算术游戏运用到教学中,数学老师张先彬还有很多招数。比如在小学一年级新生学到三角形、正方形、圆形的时候,引入找茬游戏,让孩子们在找茬游戏中辨别并记忆各种图形。

魔方也是教学重要道具。魔方非常有助于孩子智力发展,在玩魔方的过程中,可以学到图形的平面变化、空间变化,培养孩子的空间感。张先彬说。

此外,张先彬还要求孩子们写日记,当然,不是传统的语文课日记,而是数学日记。在孩子们的日记本上,密密麻麻地写着每天数学课的收获、思考过程。少则几十字,多则三四百字。

其实我没有要求字数,只要他们能写出数学学习中的思考,我就会努力抓住他们的闪光点,并运用到教学过程中。

张先彬说,你光是从数字答案中是看不出孩子的学习过程和思维的,只有通过孩子的表达,才能发现,培养孩子的数学思维比获取数学知识更关键,但这是个漫长的过程。

24点挑战赛

张先彬的17份教案中的最后一份是24点挑战赛。挑战赛有30题,其中部分题目比较基础,也有部分比较难,读者朋友们也来做一做,看能不能解答出这8组题目。

规则:用加减乘除四则运算,使每组数字运算结果为24,每个数字都必须使用,其中J、Q、K都代表10,A代表1。

答案:

1(8+8)9629(9-6)8

39(10-8))+649(610)+9

58(9-7)+86(108)-(78)

79(10-7)888(10-8)+8

第二篇:五子棋游戏总体设计与实现

4.系统总体设计与实现

4.1 总体设计分析

总体设计是软件开发过程中的另一个重要阶段,在这一阶段中将根据需求分析中提出的逻辑模型,科学合理地进行物理模型的设计。这个阶段的主要目标是将反映用户信息需求的逻辑方案转换成物理方案,并为下一阶段提供必要的技术资料。

4.1.1 总体设计原则

(1)整体性:软件是作为统一整体而存在的。因此,在总体设计中要从整个软件的角度进行考虑。

(2)灵活性:为保持软件长久的生命力,要求该手机游戏软件具有很强的环境适应性。为此,游戏软件应具有较好的开放性和结构的可变性。

(3)可靠性:可靠性是指软件抵御外界干扰的能力及受外界干扰时的恢复能力。

(4)经济性:经济性是指在满足游戏软件需求的前提下,尽可能地减小游戏软件的开销。

4.1.2 软件模块总体设计

软件中各模块之间的关系通常利用层次图来表示。它是一种一系列多层次的用树形结构的矩形框描绘数据的层次结构框图。一个单独的矩形框作为树形结构的顶层,各个数据的子集由下面的各层矩形框代表,最底层的各个矩形框代表组成这个数据的实际数据元素(不能再分割的元素),它代表完整的数据结构。这模式非常适合于需求分析阶段的需要,层次方框图对数据结构描绘随着结构精细化也越来越详细。反复细化沿着图中每条路径,从对顶层信息的分类开始,直到确定了数据结构的全部细节为止。

开始游戏重新游戏游戏选项悔棋认输五子棋游戏背景音乐退出游戏先后手设置游戏设置棋盘底纹设置棋盘大小设置游戏帮助帮助关于 图4-1 游戏功能结构

本研究中将游戏软件分为三大模块,如图4-1所示,包括:游戏选项、游戏设置和帮助。按照在调研中搜集的资料对每个模块的功能进行编排制作。依据上述功能的分析,本研究中,将游戏软件在三大模块的基础上又对每一大模块又分为几个子模块:

游戏选项包括六个模块:开始游戏、重新游戏、悔棋、认输、背景音乐和退出游戏。

游戏设置包括三个模块:先后手设置、棋盘底纹颜色设置和棋盘大小设置。

帮助包括两个模块:游戏帮助和关于。

4.2 游戏设计

4.2.1 游戏前的准备

本游戏在开发之前需要做一些前期准备工作,尤其是对于精通五子棋游戏的Java 游戏开发者来说。通常情况下,一款运用起来比较熟练地 J2ME 开发工具

是必不可少的。本游戏使用的是J2ME的简化开发工具 Sun Java (TM) Wireless Toolkit 2.5.2 for CLDC,他需先将Java虚拟机安装调试好之后才能使用。WTK 2.5.2 不带有文本编辑功能,所以需要另寻搭配使用。本游戏采用 Ultra Edit 进行编辑。本游戏需要几张后缀名为.png格式的卡通图,除了一张用作五子棋游戏的 Logo 外,其余的都将在游戏中使用。 4.2.2 游戏界面和事件驱动设计

游戏的界面设计采取传统游戏界面风格,如图4-2所示。游戏设计中采用传统界面游戏风格,首先启动游戏,然后进入游戏开始界面,界面中放置“设置”、“开局”、“帮助”、“关于”四个选项供玩家选择。其中“设置”选项主要是对游戏的相关功能进行设置,如游戏难度设置。另外还有“悔棋”、“重玩”等项目的设置。除此之外还包括查看游戏帮助、游戏介绍等。

图4-2 游戏界面设计

所谓事件驱动,简单地说就是你点什么按钮(即产生什么事件),电脑执行什么操作(即调用什么函数)。当然事件不仅限于用户的操作。我们知道,事件是事件驱动的核心自然是。从事件角度说,一个事件收集器、一个事件发送器和一个事

件处理器组成了事件驱动程序的基本结构。事件收集器专门负责收集包括来自硬件的(如时钟事件等)、来自用户的(如键盘、鼠标事件等)及来自软件的(如应用程序本身、操作系统等)的所有事件。将收集器收集到的事件分发到目标对象中则由事件发送器负责完成。具体的事件响应工作则由事件处理器完成,它需要运用虚函数机制(函数名取为类似于 Handle Msg 的一个名字),它往往要到实现阶段才完全确定。事件处理器对于框架的使用者来说是他们唯一能够看到的。 棋类游戏通常具备两个重要特性,首先是对战双方轮流落子,其次是落子间隔通常是不确定的,尤其是对战后期,可能每一步棋都要经过深思熟虑,无论是人还是计算机,都无法对时间间隔有事先的预期。基于以上两个特性,本游戏摒弃了大多数游戏采用的线程或定时器驱动游戏的方法,而采用了事件驱动的方法,即玩家的键盘或触摸笔触发游戏的下一个动作。事件驱动大大减少了不必要的工作量,只有玩家发出消息时,计算机才启动运算,而在玩家思考期间,计算机不做任何运算和重绘操作。 4.2.3 游戏的类设计

五子棋游戏属于二维棋类游戏,因此可以定义一个 Chesses 类来表示棋子,用一个 Chess 类型的二维数组来包含棋盘上的所有棋子,对于该棋子玩家的区分使用Chesses 的 boolean 型的变量 is Player1 来区分。可以考虑直接生成数组的每一个对象而不是在数组建立后,而是把每一个棋子对象(Chesses)放在游戏的进行中生成,这主要是考虑到移动设备的资源有限,尽可能减少系统资源占用。这样在游戏进行时,可以避免还没有下的棋子在一开始就占用了系统内存,玩家每下一步棋,在数组相应位置生成该棋子的对象。

对于游戏中的每一类的设计,首先就是一个 MIDlet 类,Gobang 类继承自MIDlet 类,通过方法 start App,pause App,destroy App 来通知游戏的开始,暂停和销毁结束,用于连接设备的应用程序管理器(Application Manager)。

本游戏共由7个类组成,它们各自的功能如下:

(1) Gobang MIDlet类

负责程序的启动和屏幕之间的切换;

(2) Gobang Canvas 类

玩家的对战平台,他继承于 Canvas 类; (3) Setting 类

用于创建游戏的各项设置参数表单;

(4) Gobang Logic 类

游戏的逻辑类,负责胜负判断和计算机落子;

(5) Dot 类

棋子类,包含了棋子的位置信息; (6) Help 类

游戏的帮助类,包含五子棋的一些常识信息和五子棋教学内容; (7) About类

游戏的关于类,包含游戏的版本、版权等信息。 各个类之间的关系如图4-3所示:

图4-3游戏类设计

4.2.4 游戏的流程设计

对于棋盘界面的更新,游戏进行绘制棋子时是按照棋子的二维数组来完成的,玩家下棋后,设置is Player1 值,程序修改数组相应位置,然后重新绘制(repaint)。为了使游戏的操作尽可能的简便,本文设计上不在游戏进入时设计菜

单,玩家可以直接开始对战,而是在开始游戏的过程中设置重新开始和退出的按钮。即一键开始,运行即玩,重来或退出都使用一键操作。 游戏流程的设计依据主要是游戏的界面设计和游戏的类的设计。 游戏启动时,Gobang MIDlet 对象先显示游戏的主屏幕,在屏幕下方一侧是出软键(软键指描述抽象客户端设备如何显示),另一侧是用软件构成的菜单,菜单元素主要有“开局”、“游戏设置”、“游戏帮助”、“关于”选项。当玩家选择“游戏设置”软键时,则显示游戏参数设置表单;当玩家选择“开局”软键时,则显示游戏对战主界面;当玩家选择“游戏帮助”软键时,则显示游戏帮助表单;当玩家选择“关于”软键时,则显示游戏关于表单。 玩家进入游戏参数设置表单,当玩家按下“确定”软键时,则确认当前游戏参数,返回游戏主屏幕;当玩家按下“取消”软键时,则放弃此次对游戏的修改,直接返回游戏主屏幕。 玩家进入游戏对战画布,对战中画布有两个软键,当玩家按下“返回主菜单”软键时,则退出游戏到达游戏主菜单;当玩家按下“悔棋”软键时,则进行悔棋操作;当游戏结束时,“悔棋”软键被换成了“重玩”软键。 玩家进入游戏介绍表单,当玩家按下“确定”软键时,返回游戏主屏幕。 4.2.5 游戏算法的设计

1、五子棋的获胜组合

有哪些获胜组合是在一场五子棋的游戏中计算机必须要知道的,因此,获胜组合的总数必须要求得。在本文中我们假定当前的棋盘为15*15:

(1)每一列的获胜组合是11,共15列,计算水平方向的获胜组合数,所以水平方向的获胜组合数为:11*15=165。

(2)每一行的获胜组合是11,共15列,则可计算垂直方向的获胜组合总数,垂直方向的获胜组合数为:11*15=165。

(3)同理,可计算正对角线方向的获胜组合总数,正对角线上的获胜组合总数为11+(10+9+8+7+6+5+4+3+2+1)*2=121。

(4)计算反对角线上的获胜组合总数。计算反对角线方向的获胜组合总数可计算为11+(10+9+8+7+6+5+4+3+2+1)*2=121。这样可计算得所有的获胜组合数为:165+165+121+121=572。

2、设计获胜棋型

通过上面的计算,一个15*15的屋子棋盘在此已经计算出了会有572中获胜方式,因此,我们就可以利用数组建立一些常规棋型,棋型的主要作用是:

(1)判断是否有任何一方获胜;

(2)根据当前格局判断最可能的落子方式。

然而在现实中,高手留给我们的经验就是把握前奏,如“冲四”、“活三”,除了“连五”以外,这些也是同向胜利的捷径。

3、攻击与防守

获胜棋型的算法是中性的,不区分计算机和玩家,这就涉及到攻击和防守何者优先的问题。而许多高手都认为五子棋的根本是“防守”,“攻击”是灵魂。进攻是取胜的手段,是防守的延续和发展。许多经验和研究表明,一个棋手只要掌握了全面的、基本的防守原理和技巧,就能和比自己棋力高一个等级的进攻型选手对抗,起码能立于不败之地。对手进过越偏激,则防守的效果越好。没有进攻的防守就像只开花不结果,没有实际意义,顽强的防守是反攻的前奏,没有进攻的延续,防守也失去了价值。而这缺一不可。根据以上原理,计算机在接受最佳的攻击位置之前,还要计算当前玩家的最佳攻击位置。如果玩家存在最佳攻击位置,那么计算机就将下一步的棋子摆在玩家的最佳攻击位置上以阻止玩家的进攻,否则计算机便将棋子下在自己的最佳攻击位置上进行攻击。

4、用到的典型算法 (1)坐标变换算法

游戏的实质其实是对所下棋子的位置进行操作和判断,因此将己方、对方以及棋盘上空点的位置坐标存储在相应的List中。我对所下棋子的坐标进行了处理,因为我所采用的棋盘为15*15,所以棋子横坐标为0到14的整数,纵坐标也为0到14的整数。因此,每次在棋盘上下子之后,计算机在存储该点的坐标时,便要对坐标进行加工。假设左上角点为firstPoint,它的实际坐标为(x1,y1),而我是将它作为(0,0)存储的,其它的坐标,其它点都是以该点为标准进行变换的,假设棋盘上每个格子的宽度为w,某实际点为(x2,y2),变换后的坐标为(x,y),x=(x2-x1)/w,y=(y2-y1)/w。

(2)胜负判断算法

胜负判断的规则很简单,就是判断游戏双方的棋子在同一条水平线、同一条竖线或是同一条斜线上谁先出现5个连续的棋子,谁先达到这样的目标,谁就获得胜利。在本设计中,是在每次下完一个子后进行判断,看己方是否达到了胜利的标准,若胜利游戏便结束;否则,游戏继续。

(3)人工智能算法

人工智能算法的主体思想分为以下三个步骤:

第一步:根据双方的当前的形势循环地假设性的分别给自己和对方下一子(在某个范围内下子),并判断此棋子能带来的形势上的变化,如能不能冲4,能不能形成我方或敌方双3等。

第二步:根据上一步结果,组合每一步棋子所带来的所有结果(如某一步棋子可能形成我方1个活3,1个冲4(我叫它半活4)等),包括敌方和我方的。

第三步:根据用户给的规则对上一步结果进行排序,并选子(有进攻形、防守形规则)。

5、典型类的具体设计 (1)应用程序类

Gobang 类用于连接设备的应用程序管理器(Application Manager),Gobang类继承自 MIDlet 类,通过 Gobang 类的方法 start App,pause App,destroy App 来通知游戏的开始,暂停和销毁结束。源代码如下:

package com.occo.j2me.game.gobang; import javax.microedition.lcdui.Display;

import javax.microedition.midlet.MIDlet;public class Gobang extends MIDlet

//定义游戏界面的 Canvas 类 Gobang Canvas 的对象 Gobang public { Gobang Canvas gobang; Gobang() {

super();

gobang=new Gobang Canvas(this);//生成 Gobang Canvas 类的对象 gobang

} protected void start App(){

Display.get Display(this).set Current(gobang);

} protected void pause App(){

} protected void destroy App(boolean arg0){

}} //在屏幕上绘出游戏见面 gobang (2)游戏界面类

Gobang Canvas 类继承自 Canvas,游戏的核心类是 Gobang Canvas 类,此类将完成游戏的绘图、互动、控制、逻辑、等所有功能,此类的框架代码如下:

Package com.occo.j2me.game.gobang; import javax.microedition.lcdui.Displayable; import javax.microedition.lcdui.Command; import javax.microedition.lcdui.Canvas;

import javax.microedition.lcdui.Command Listener; public Gobang Canvas(Gobang gobang){

this.gobang=gobang;

}

protected void paint(Graphics g) {

}

import javax.microedition.lcdui.Graphics;public class Gobang Canvas extends Canvas implements Command Listener{protected Gobang gobang;

public Gobang Canvas(){

}

} (3)棋子类

整个棋盘是一个 Chesses 类型的二维数组,棋盘上的每一个棋子都对应着一个Chesses 的对象,此类定义了一个棋子,源代码如下:

package com.occo.j2me.game.gobang; public Chesses() {

}

public class Chesses {boolean is Player1;

public Chesses(boolean is Player1) {

this.is Player1=is Player1;

}}

4.3 游戏实现

4.3.1 主类的实现

YpkWuZiQiActivity类是五子棋游戏的主类,同时也是五子棋游戏的入口,它继承自Activity类。进入程序后,首先调用init()方法,init()方法通过调用setContentView(R.layout.welcomeview)显示登录该游戏的第一个界面。welcomeview.xml是一个布局文件,里面存储了界面信息。该界面中有四个Button,分别为welButton

1、welButton

12、welButton

3、 welButton4,点击每个Button都会触发一个事件,其中点击welButton1和welButton2还会给它的成员变量FIGHTINGMODE赋值,因为在人人对战和人机对战是写在同一个ChessBoard类中的,所以需要通过FIGHTINGMODE的值来区分是人人对战还是人机对战。

点击welButton1时,FIGHTINGMODE=1,然后会调用initTwo()方法,该方法通过调用setContentView(R.layout.chess)方法,来显示对战的界面。chess.xml文件存储了对战界面的信息。在chess.xml文件中调用了ChessBoard类,该类中主要定义了棋盘的信息,下文会对该类做具体的介绍的。在对战界面中也有四个Button,分别是b

1、b

2、b

3、b4。

首先来介绍一下b2,该Button的功能是返回主页,调用init()方法就可以实现。b3的功能是重新开始,这个也只需要调用initTwo()方法。b3的功能是退出,调用了系统方法:System.exit(1)。下面重点介绍一下b1,该Button的功能是悔棋。该Button设定的点击事件详细内容如下:

b1.setOnClickListener(new OnClickListener(){ public void onClick(View v){ ChessBoard chess = (ChessBoard)findViewById(R.id.chess); Point temp = null; if(chess.whoRun == 1){

if(chess.firstPlayer.getMyPoints().size()>=1 &&chess.secondPlayer !=null){ temp=chess.secondPlayer.getMyPoints().get(chess.secondPlayer.getMyPoints().size()-1);

chess.secondPlayer.getMyPoints().remove(temp); chess.freePoints.add(temp); temp=chess.firstPlayer.getMyPoints().get(chess.firstPlayer.getMyPoints().size()-1); chess.firstPlayer.getMyPoints().remove(temp); chess.freePoints.add(temp); chess.freshCanvas();

}

} if(chess.whoRun == 2){ if(chess.firstPlayer.getMyPoints().size()>=1 && chess.secondPlayer !=null){ temp=chess.firstPlayer.getMyPoints().get(chess.firstPlayer.getMyPoints().size()-1); chess.firstPlayer.getMyPoints().remove(temp); chess.freePoints.add(temp); temp=chess.secondPlayer.getMyPoints().get(chess.secondPlayer.getMyPoints().size()-1); chess.secondPlayer.getMyPoints().remove(temp); chess.freePoints.add(temp); chess.freshCanvas();

} }) 首先获取ChessBoard对象,该对象继承自View,详细的定义了棋盘信息,主要负责显示棋盘的内容。接下来判断一下触发悔棋事件的是哪一个玩家,再判断是否符合悔棋的条件,这个条件很简单,就是棋盘上至少要有两个棋子。之后便进行悔棋操作,分别将两个玩家最后下的棋子取出,程序实现就是将两个ArrayList的最后一个元素remove出来,再分别放到记录棋盘中没有棋子的点的

}

}

集合中,最后更新一下画布,主要是调用ChessBoard的invalidate()方法。通过以上步骤之后,呈现在我们面前的便是悔完棋的画面了。

点击welButton2时,FIGHTINGMODE=2,之后的步骤便会点击welButton1是相同的了,不同的是,由于对战模式的改变,从人人对战变成了人机对战。

点击welButton

3时

initThree()

用setContentView(R.layout.netchess)方法实现网络对战。详细的对战实现细节将会在下文一一介绍。在这个界面中只保留了两个Button:b2和b4。这两个Button所实现的功能和上面的b2和b4是相同的。

最后,welButton4比较简单。它所实现的功能为退出应用程序,调用System.exit(1)方法。 4.3.2 游戏设置类的实现

游戏设置表单用来对游戏参数进行设置,包括棋盘大小、先手选择、智能级别。表单中使用了 Gauge 和 Choice Group 两种高级用户界面组件。

1、棋盘尺寸选择

标准的五子棋棋盘为 15*15,但为了满足不同玩家的需求,这里提供了大小为10*10 到 20*20 的棋盘,用户可以通过 Gauge 组件改变。棋盘的最小值为 10,而Gauge 组件的最小值为 0,所以当前的 Gauge 值需要角上 10 才是当前棋盘大小。创建 Gauge 组件的代码如下:

form = new Form(" 游戏设置"); // 创建参数设置表单并添加标签 gauge Size = new Gauge("棋盘规格: " + board Size + " X " + board Size, true, 10, board Size - 10); //棋盘规格

form.append(gauge Size);

图4-4 棋盘尺寸的设计

在Gauge交互模式下可以为Gauge对象所在的表单对象绑定一个Item State Listener 事件监听器,并在监听器上捕捉 Gauge 对象的事件,当 Gauge 的值发生变化时就会触发事件。这里将根据 Gauge 的当前值改变标签,显示当前的棋盘大小。其代码如下:

public void item State Changed(Item item) {

if(item == gauge Size) //当 Gauge 组件发生变化时

{

int bs = gauge Size.get Value() + 10; //获取当前的 Gauge 值并计算棋盘大小(加10)

gauge Size.set Label("棋盘规格: " + bs + " X " + bs); //改变 Gauge 组件的标签

}

}

2、难度选择

游戏的难易程度根据计算机的智能级别来控制,创建及添加选项的方法和复选框一样,所不同的是在创建 Choice Group 对象时,类型设置为 1(单选)。对于单选框,set Selected Index 只能用来指定某个选项被选中,因此,布尔值 selected 的值必然为 true,否则便没有意义。

游戏共有 3 个难度级别,分别是:拜师学艺、棋行天下、谁与争锋(此游戏中并未作出区分),初始情况下为拜师学艺,该选项的索引值为 0。创建难度选择单选框的代码如下:

level = 1; //默认情况下的难度级别

choicelevel = new Choice Group("电脑智能级别:", 1); //创建难度级别选项组 choicelevel.append("拜师学艺", null); //难度 1 choicelevel.append("棋行天下", null); //难度 2 choicelevel.append("谁与争锋", null); //难度 3

choicelevel.set Selected Index(level-1 , true); //设置默认情况为难度 1,索引值为0

form.append(choicelevel); //将选项组添加到主表单中

游戏设置选项表单还有两个 Command 对象,分别用于玩家却热和取消,所以表单需要监听软键事件和组件事件:

public class Setting implements Command Listener, Item State Listener

3、棋手选择

选择先手和难度等级用 Choice Group 组件来实现。 Choice Group 组件用来构造选择框,其构造函数如下:

Choice Group(String label, int choice Type) 选择先手的选项框为选择组件,属性为复选框,标签名为空。创建好选择组件后,逐条添加选项元素。添加选项的方法如下:

int append(String string Part, Image image Part) 该方法追加一个选项元素到选择组中,追加的选项为选择组中的最后一个元素,选择组的大小加 1。

对于多选类型的 Choice Group,还可以设置个别选项的选择状态。设置初始选择状态的方法如下:

void set Selected Index(int element Num, Boolean selected) 这里创建一个只有一个选项元素的多选框用于玩家设置是否计算机先行,在默认情况下为true,创建完成多选框后将其添加到主表单中,代码如下:

Computer First = true; //在默认情况下为计算机先行 choice First = new Choice Group(null, 2); //创建复选框 choice First.append("电脑先手", null); //添加选项元素

choice First.set Selected Index(0, Computer First); //设置多选框的默认状态 form.append(choice First); //将多选框添加到主表单中 4.3.3 棋子类的实现

1、棋子的行列位置

此五子棋游戏是一个二维棋类游戏,所以定了了一个 Dot 类来表示棋子。由于移动设备的局限性,所以程序不在下每一步棋时生成一个对象,而是在游戏进行时,玩家或者计算机没下一步棋,在数组相应位置生成该棋子的对象,而将已经下过的棋子保存到数组中随时检索,这样可以避免过多棋子对象占用系统内存。Dot 类的 UML 图如图 4-5 所示:

图4-5棋子行列设计

Dot 类主要有两个变量 row 和 col,分别表示行和列:

public int row; //行

public int col; //列

2、检查越位

棋子的位置并非是任意的,玩家和计算机每走一步棋之前都要线检查该位置的合法性,即棋子是否在棋盘上,否则判为无效落子。检查是否越界的代码如下:

public boolean is In Board(int board Size) //判断棋子是否越界(超出棋盘) { return row >= 0 && row < board Size && col >= 0 && col < board Size; }

3、修改棋子位置

在创建好 Dot 对象后,Dot 类提供了两种方法更改棋子位置,包括设置行列位置和从已有棋子中复制参数。

public void set Row Col(int r, int c) //设置棋子位置

{

row = r; col = c;

}

public void copy From(Dot d) //复制已有的棋子

{

row = d.row;

col = d.col;

} 4.3.4 对战逻辑类的实现

1、建立数据结构

本程序以数组保存当前盘面的情况,每个位置可能有三种状态:空、玩家的落子、计算机的落子,分别用 0、

1、2 来表示。代码如下:

public static int PLAYER_NONE = 0; //该位置为空

public static int PLAYER_COMPUTER = 1; //该位置有电脑的落子

public static int PLAYER_HUMAN = 2; //该位置有玩家的落子

棋盘在初始情况下为空,即棋子上没有任何棋子,在Gobang Logic类的构造函数中对棋盘进行初始化:

table = new int[board Size][board Size];//创建棋盘数组 for(int r = 0; r < board Size; r++) {

for(int c = 0; c < board Size; c++)

table[r][c] = 0; //初始化盘面为空 }

除了记录棋盘上每个位置的落子状态外,程序还将对每种状态的位置个数进行统计,以对算法进行简化。对三种状态的统计存储在整型数组中,该数组为全局变量。

private int player Counter[];

在 Gobang Logic 类的构造函数中对三种状态的计数进行初始化,即棋盘上都是空、计算机的落子或玩家的落子状态的个数为 0,在数据结构上,把空也当做某一特殊玩家。

初始化代码如下:

player Counter = new int[3]; //落子状态计数器

player Counter[0] = board Size * board Size; //整个棋盘都是空的状态 player Counter[1] = 0; //电脑落子0 player Counter[2] = 0; //玩家落子0

2、落子和悔棋

这里使用了一个 Dot 类棋子对象来记录最后一步棋的位置,当玩家下了一步棋后需要将上一步重新绘制,以消除旗子上的引导框。另外,还是用了堆栈来存储最近的几步落子,以便玩家悔棋。

private Dot last Dot; //棋子对象,存储最后一步落子 private Stack steps; //棋子对象的堆栈

最后一步棋子和棋子堆栈在 Gobang Logic 类的构造函数中进行初始化;

last Dot = new Dot(board Size); //创建棋子对象用来存储最后一步棋,初始化

位置为棋盘中央steps = new Stack();//堆栈对象,用来存储最近的几部棋在棋盘上落子的代码如下:

private void go At(int row, int col, int player) //电脑或人在 row、col 位置上走

{

int last Row = last Dot.row; //记录上一步的行坐标

int last Col = last Dot.col; //记录上一步的列坐标

table[row][col] = player; //当前位置填充玩家代码

last Dot.set Row Col(row, col); //将这一部设置为“最后一步”

game Canvas.repaint At(last Row, last Col); //重新绘制上一步(将引导框去掉)

game Canvas.repaint At(row, col); //绘制当前这步

switch(player) //统计双方落子数量

{

case 1:

player Counter[1]++; //电脑的步数

break;

case 2:

player Counter[2]++; //玩家的步数

break;

}

player Counter[0]--; //空白的个数

if(steps.size() > 10) //堆栈数量超过上限(10)

steps.remove Element At(0); //清除栈底

steps.push(new Dot(row, col)); //将当前这步棋子压入堆栈

}

Stack(堆栈类)从 Vector 集成而来,它使用 push()方法进入堆栈,需要时使用 pop()方法从堆栈的顶部将其取出。悔棋动作由玩家做出,从数据结构来看,是同时后退两步(将最后两步棋位置的落子状态设置为空)。

Stack 类的 peek()方法将获取栈顶对象,但不移。悔棋代码如下: :

public boolean undo()//悔棋

{

if(steps.size() >= 3)

{

Dot d = new Dot();//创建棋子对象

d.copy From((Dot)steps.pop());//从堆栈弹出的棋子中复制行列位置坐标

table[d.row][d.col] = 0;//将该位置设置为空

game Canvas.repaint At(d.row, d.col); //在棋盘上重新绘制该位置

d.copy From((Dot)steps.pop());//从堆栈弹出的棋子中复制行列位置坐标

table[d.row][d.col] = 0; //将该位置设置为空

game Canvas.repaint At(d.row, d.col); //在棋盘上重新绘制该位置

d.copy From((Dot)steps.peek());//获取栈顶对象,作为最后一步棋存储 last Dot.copy From(d);

game Canvas.repaint At(d.row, d.col); //重新绘制最后一步(添加引导框) return true; //悔棋成功

}

else

{

return false;

//悔棋失败

}

} 4.4 本章小结

本章主要内容是游戏的实现,包括主类的实现,如构造函数、事件处理等,游戏帮助和介绍表单类的实现,游戏设置类的实现,如棋盘、选手、难度等,旗子类的实现,如棋子行列位置、检查越界等,对战逻辑类的实现,如落子和悔棋、逻辑运算等的实现。

第三篇:基于C语言五子棋小游戏

五子棋小游戏

一.需求分析

现在有越来越多的人使用电脑,而且五子棋的受众广泛但实体棋操作较为繁琐且平时较难实现,所以电脑版的五子棋游戏应运而生。大家对于这个小游戏的需求如下:首先,设计这个游戏最基本的就是实现玩家之间对战,玩家可以通过某些操作来实现对战功能;有时候可能由于时间等原因,玩家可能需要保存游戏,此时需要一个“保存”功能;有时候可能玩家由于失误会走错棋,此时就需要“悔棋”功能;有时候玩家可能觉得这局游戏玩的非常不好,这时候就需要“重新开始游戏”功能;玩家在玩过游戏之后有可能想保存游戏记录便于以后分析此时就需要“排行榜”功能;有些玩家在玩游戏时喜欢听音乐,这时候就需要在下棋时可以播放背景音乐的功能;最基本的通过输入坐标来实现落子的操作方式很繁琐而且很不方便,这时候就可以将落子机制改为更直观的光标移动模式。

二.设计思路

1.玩家对战功能:在玩家对战功能中,玩家可以通过按方向键来移动光标、按空格来实现落子,最终在横或竖或斜方向上达成五个相同颜色的棋子来获得胜利。 基本思路:

(1)使用二维数组保存棋局。

(2)由于要使用光标,所以使用输出缓冲器。

(3)打印棋盘。

主要使用Print()函数来算出棋盘并将缓冲器内容输出。

其余为其中调用的辅助函数。chessPrint()是打印交点坐标的字符的函数;getCurse()是打印光标的函数;write()函数是用来向缓冲器里面写入字符串的函数;ln()函数是负责将缓冲器写入位置提行的函数;Display()函数是将缓冲器中内容输出到屏幕的函数。

(4)下子,在后文有详细介绍。 (5)胜负平判断

调用Check()函数进行四个方向的检查,检查是否有五子连珠。

判断完毕后输出结果(如果存在结果)

2.保存游戏和装载游戏功能:在游戏过程中,只要按“1”键就可以保存游戏到指定名称的文档中;在游戏开始界面,只要按“2”选择“load board”就可以装载指定名称的游戏。 基本思路:

调用saveGame()函数将当前棋局的相关信息全部保存到结构体变量saveChess中,并将其中的内容全部保存到文件里。

加载时将结构体变量里的数据全部读出,赋给当前棋局相关信息变量,之后正常运行游戏即可。

3.悔棋功能:在游戏过程中,只要按“2”键就可以返回到上一步的局面。 基本思路:

玩家对战时,每个玩家每次成功落子之后,棋盘的相关信息就会被记录到一个结构体数组里。

每次悔棋时,就调用一个函数把储存在结构体数组里的上一回合的信息全部赋给当前棋局信息变量。

4.重新开始游戏功能:在游戏过程中,只要按“3”键就可以初始化棋局,重新开始游戏。 基本思路:

玩家对战时每一次重新开始游戏就调用runGame()函数,并返回当前玩家信息。

人机对战时每一重新开始游戏就调用自身,并返回当前玩家信息。

5.排行榜功能:在一局游戏结束时,按照提示输入“1”则可以将自己的名字及成绩保存到排行榜文件中。在游戏开始界面,只要按“3”就可以查看排行榜。(排行榜按照步数由小到大,棋色又白到黑排序) 基本思路:

一局游戏结束时调用inList()函数,inList()函数又调用addList()函数,将关于棋局的部分信息保存到文件。

关于排序设置了单独的函数sortList()函数,其在addList()里面被调用。此处使用了结构体数组,按照其中的“步数”成员将结构体数组中的元素进行“冒泡排序”。

这里比较特别的是,每次都是先将要加入的内容写到文件末尾,再将文件中所有内容读出后进行排序,最后再将排好序的内容全部写入文件。

6.背景音乐功能:在游戏过程中会一直循环播放音乐,带给玩家不一样的享受。 基本思路:

使用Windows.h头文件,并加上相关指令

再调用PlaySoundA()函数就可以实现循环播放背景音乐。

7.使用光标定位棋子:使用方向键控制光标移动方向,使用空格键来实现落子,带给玩家比坐标落子更高级的体验,更加方便快捷。(此处使用了以前没用到的

,调用getch()函数,为了不需要键入回车。) 基本思路:

光标实现:使用缓冲器将棋盘交点的间隔都填充内容,光标用制表符表示,其余为空格。 方向键移动光标:

防止越界:

空格落子:

8.简单的人机对战:主要防御型的AI,主要针对对手的棋型来安排战术,有时会选择进攻。 基本思路:

判断对手是否有2,3,4子连珠,如果有,电脑会在两头下子;如果没有,若己方在一侧存在3子或4子连珠,电脑会在后面补子;如果以上情况均未出现,电脑会随机在对手单子周边落子。其余基本功能同人人对战,但是不支持保存和读取棋局功能。

按照奇偶数来判断是该电脑走子还是玩家走子。电脑执黑则会有不同的初始化方法。

三.用户手册

1.如何运行程序

2.如何开始游戏(包括玩家对战和人机对战) 3.如何退出游戏 4.如何进行游戏

5.如何保存当前游戏(仅支持玩家对战) 6.如何读取已保存的游戏(仅支持玩家对战) 7.如何重新开始游戏(支持人机和玩家对战)

8.如何保存记录(支持人机和玩家对战,不加区分)

9.如何调取记录进行查看(支持人机和玩家对战,不加区分) 10.如何查看游戏规则

11.如何了解设计师相关信息

12.如何悔棋(支持人机和玩家对战)

1.如何运行程序 第一步,打开VS2012,点击“打开项目”。

第二步,选择“高级五子棋”项目,点击“打开”

第三步,使用快捷键“Ctrl+F5”,开始运行程序,进入游戏开始界面。

2.如何开始游戏

按照开始界面中的提示操作即可,从键盘输入“1”即可开始玩家对战或人机对战(输入“1”为玩家对战,输入“2”为人机对战,人机对战时可以选择电脑的颜色)。 输入“1”之后的效果:

再输入“2”之后的效果:

再输入“1”之后的效果:

再输入“2”之后的效果:

3如何退出游戏

此处分两种情况:第一种是在开始界面,可以通过键盘输入“0”来实现退出游戏(此时会有退出界面);第二种是在游戏过程中,可以通过按“Esc”键来直接退出游戏(此时没有退出界面)。 第一种:

输入“0”之后的结果:

第二种:

按“Esc”之后的效果:

4.如何进行游戏

玩家可以通过按“↑”“↓”“←”“→”来实现光标的移动,通过按空格键来在没有棋子的位置实现落子。 初始:

按空格之后的效果:

按“→”之后的效果:

5.如何保存当前游戏

在游戏过程中,玩家可以通过按“1”来实现游戏的保存。 按“1”之后的效果:

6.如何读取已保存的游戏

在游戏开始界面,可以通过从键盘输入“2”来装载曾经保存过的游戏。 输入“2”之后的效果:

7.如何重新开始游戏

在游戏过程中,按“3”可以实现游戏的重新开始。 初始:

按“3”之后的效果:

8.如何保存记录

在一局游戏结束后,会有如下文字提示:

输入“1”后的效果:

9.如何调取记录进行查看

在游戏开始界面,可以通过键盘输入“3”来查看排行榜内容。

10.如何查看游戏规则

在游戏开始界面可以通过键盘输入“4”来查看游戏规则。

11.如何了解设计师相关信息

在游戏开始界面输入“5”即可了解设计师相关信息。

12.如何悔棋

在游戏过程中,可以按“2”来实现悔棋,即恢复到上一步的状态。 初始:

按“2”之后的效果:

四.总结

通过本次五子棋大作业,我初步掌握了运用之前学过的知识去开拓未知领域的能力、借鉴与发展能力、自学能力等多项技能。总的来说我感觉这次大作业的难度是比较大的,这其中会面临很多选择,这恰恰是考验我们能力的地方。例如,“排行榜”功能就可以选择是使用链表来做还是使用结构体数组来做。我一开始的思路是使用链表来做,但是由于我链表的相关知识掌握的不是很熟练所以屡屡受挫,最终我决定改变思路,使用结构体数组来做,果然要容易一些,我也成功的实现了排行榜功能。再比如,好多同学都是选用EasyX来实现鼠标控制,我本来一开始也想尝试,但是后来经过努力发现这种模式的难度对我来说偏高,所以我借鉴了一下网上的一些五子棋源代码,最终决定使用光标这种比坐标略强、比鼠标略弱的操作模式。这样的例子在开发过程中还有很多,在这里我就不一一列举了。总而言之,我从这次大作业中收获了很多专业知识,更重要的是我掌握很多以前没有的能力。

第四篇:QT基于linux的五子棋游戏设计与实现

课题名称:基于linux的五子棋游戏设计与实现

专业:计算机科学与技术(计算机工程方向)

开发工具及语言:,ubuntu12.04,QT

运行环境:linux下的QT

论文字数:1w左右

是否需要PPT:是

是否需要安装说明:是

所在城市:武汉市

所在学校:华中农业大学楚天学院

功能需求分析

系统的基本功能需求分析如下:

(1) 游戏进入界面的菜单选择,有自我对战、人机对战、网络对战和退出 游戏四个选项;

(2) 进入游戏之后,显示一个十三行十三列的五子棋的棋盘。棋盘旁边显 示一个菜单,菜单选项有棋局重现、继续上步、上级菜单和退出游戏,在界面上可以在棋盘落子操作和菜单操作之间进行切换,用键盘的按键来控制,棋局重现功能是在某方胜利之后才能手动操作一步步查看并回顾双方下棋的过程;继续上步可以切换回棋盘操作;上级菜单功能可以使五子棋游戏退出当前的游戏模块(自我对战、人机对战、网络对战其中的一种),回到游戏开始界面时候的菜单,进行重新选择;退出游戏是退出整个游戏界面;

(3) 棋盘上显示光标,可以对光标进行移动操作,也可以在棋盘和菜单来 回切换的时候重绘和擦除;

(4) 在上面棋盘将光标移动到上面对应的位置,可以落子,棋盘上将在光 标显示处出现相应的棋子,并且棋子在横纵交点处;

(5) 自我对战的过程中有悔棋的功能;

(6) 游戏的过程中会有提示信息,如该哪一方落子,棋盘旁边显示相应按 键对应的操作列表;

(7) 可以自动判断胜负,胜利一方形成一列的五个或5个以上的棋子闪 烁数次,显示是黑方或者白方已经胜利的字样,并且停止落子的功能;

(8) 能够实现三种游戏模式,自我对战、人机对战和网络对战。

非功能需求分析

非功能需求如下:

(1) 在程序运行的过程中程序不能崩溃,更不能使系统出现问题,造成 灾难性的后果;

(2) 希望在此项目的基础上不做改动或做很少的改动就能在其他的系统 或设备上运行;

(3) 界面清晰容易看懂,方便玩家操作;

(4) 游戏运行速度不能太慢,要反应及时,以免影响玩家的兴趣。

(5) 程序代码必须每行都有详细注释。 以上是要登记的内容。这个是例子。自己修改相关信息。一定要写的详细,开发以文档为依据。 注意请把文件名换成自己的作品名,以防技术开发错误

注意事项:

第五篇:趣味亲子游戏

任务1:收玩具

可将玩具桶或收纳箱(盒)分类编号,如此将玩具收起来时,简单、不占空间。告诉宝宝他的玩具分别在哪,下次要玩从哪拿出来还要再放回去,培养他的秩序感。

如拼图、积木等小型组装玩具,可用数字在背后编号或用贴纸贴。

任务2:收书

按书的大小归类,爸妈在收拾的时候可以和宝宝互动,跟他说“这是大的,放这里;这是小的,放这里。”如此可让宝宝培养成就感及懂得爱惜书本。

简单的书本收拾工作,可以让宝宝一起完成,但是不建议让他们来收报纸,因为报纸有油墨,容易让宝宝不小心手沾到而食入,应避免让他们接触。

任务3:收椅垫

可先跟宝宝玩椅垫游戏,在游戏结束后,请他跟着你一起将椅垫放回原位。

任务4:收遥控器

找个大的饼干盒,让宝宝将遥控器通通放进去,如果盒子够大,可事先在盒底画遥控器形状,让宝宝依图形去放,一方面收拾,一方面可以让宝宝学会认形状。

任务5:收拖鞋

可教宝宝将拖鞋左右配对,插在一起,再放进鞋柜里。

拖鞋的大小、颜色不一,可让宝宝学习认识大小、形状,且拖鞋柔软、没有重量,没什么危险性,适合宝宝自己收完,爸妈可放心让宝宝自己收鞋,减轻工作分量。

家务活亲子游戏-厨房

厨房的清洁整理工作较繁琐且危险,建议让宝宝做一些简单又不危险的收拾工作。宝宝在做家务时,大人一定要在旁一边指导,一边照顾,平时应尽量减少让宝宝进出厨房的时间。

任务1:收锅具

在工作台下面的储藏柜,可放简单的铁锅、铁碗、汤匙或抹布等简单又没有危险性的用品。然后和宝宝一起扮家家,和大人的用具一起玩,之后一起收。

任务2:收调味料

在煤气灶旁加装一个放调味料的置物架,每次烹调完毕,可带着宝宝将一瓶瓶的调味料放回去,还可同时教宝宝认识瓶子的形状。

任务3:垃圾入箱

告诉宝宝垃圾要放进垃圾袋或垃圾箱,可和宝宝一起玩“垃圾投篮”游戏,当然,要记得告诉宝宝把扔到地上的垃圾再捡起来放进垃圾箱哦!

上一篇:砌体工程施工协议书下一篇:趣味运动会加油口号

本站热搜