java五子棋判赢? 我用的java 二维数组初始化,然后用判赢怎么写啊…

博客分类:
java学习ing——五子棋的制作(人人对战)
自从上次完成了一次画图板,接下来的一个小项目的制作就是五子棋。包括了人人对战还有就是人机对战。这一片文章就先说一下人人对战,人机之后再来完善
先附一张效果图哈~
先来制定一个制作五子棋大体的一个思路吧:
1.要先有个窗体,有棋盘。
2.要能在上面画出棋子(也就是下棋),并且要完成黑白交替的下棋。
3.要能够判断输赢,判断是否有某个颜色的棋子五个相连。
人人的比较简单,基本的思路就是这样,然后再来一步步的完成。
制作前期的准备工作
我们可以先定义一个存放五子棋他各个属性的一个接口,这样在创建棋盘等等的地方就可以通过直接调用这个接口中的静态属性来完成。这样的好处就是在修改某一参数的时候就能够直接通过修改这个接口中的属性的数值来完成。
* 五子棋相关属性的类
public interface WZQ_config {
*设置棋盘网格行数列数为15
public static final int Row = 15;
public static final int Column = 15;
* 设置棋盘初始位置坐标
public static final int X = 30;
public static final int Y = 60;
* 设置棋子大小
public static final int Chess_size = 40;
* 设置棋盘格子大小
public static final int WZQ_JianJu = 40;
窗体界面的实现
实现五子棋界面的方法可能也是蛮多的,我知道的呢有一种是在一个窗体上面分别在指定的位置使用循环绘制横竖15条线来形成一个棋盘的网格。第二种方法是直接在一个窗体上面添加一个棋盘完整的图片,这种比较简单省事儿吧。~~但。我自己用的是绘制网格线的方法。
import java.awt.C
import java.awt.D
import java.awt.G
import javax.swing.JF
import javax.swing.JP
public class WZQ_Board extends JFrame {
public static WZQ_B
* 重载构造方法
public WZQ_Board() {
this.initUI();
* 初始化界面的方法
void initUI() {
* 设置棋盘属性
this.setTitle("吉吉的五子棋");
this.setSize(new Dimension(650, 650));
this.setResizable(false);
this.setDefaultCloseOperation(3);
this.setLocationRelativeTo(null);
this.setLayout(null);
* 添加一块棋盘
this.setLayout(null);
JPanel jp = new JPanel() {
* (non-Javadoc)定义一个匿名内部类重写paint方法
* @see javax.swing.JComponent#paint(java.awt.Graphics)
public void paint(Graphics g) {
g.setColor(Color.BLACK);
super.paint(g);
for (int i = 0; i & 15; i++) {
g.drawLine(20, 20 + i * WZQ_config.WZQ_JianJu, 20
+ (WZQ_config.Column - 1) * WZQ_config.WZQ_JianJu,
20 + i * WZQ_config.WZQ_JianJu);
for (int i = 0; i & 15; i++) {
g.drawLine(20 + i * WZQ_config.WZQ_JianJu, 20, 20 + i
* WZQ_config.WZQ_JianJu, 20
+ (WZQ_config.Column - 1) * WZQ_config.WZQ_JianJu);
g.setColor(Color.BLACK);
g.fillOval(133, 133, 15, 15);
g.fillOval(293, 133, 15, 15);
g.fillOval(453, 133, 15, 15);
g.fillOval(133, 293, 15, 15);
g.fillOval(293, 293, 15, 15);
g.fillOval(453, 293, 15, 15);
g.fillOval(133, 453, 15, 15);
g.fillOval(293, 453, 15, 15);
g.fillOval(453, 453, 15, 15);
// 重绘棋子
for (int i = 0; i & 650; i++) {
for (int j = 0; j & 650; j++) {
if (WZQ_listener.array[i][j] == "black") {
g.setColor(Color.BLACK);
g.fillOval(i, j, WZQ_config.Chess_size,
WZQ_config.Chess_size);
} else if (WZQ_listener.array[i][j] == "white") {
g.setColor(Color.WHITE);
g.fillOval(i, j, WZQ_config.Chess_size,
WZQ_config.Chess_size);
jp.setBackground(new Color(209, 167, 78));
jp.setBounds(10, 10, 602, 602);
this.add(jp);
this.setVisible(true);
g = jp.getGraphics();
* 添加监听器
WZQ_listener lis = new WZQ_listener(g);
jp.addMouseListener(lis);
这里绘制棋盘的方法是重写在他的重绘方法当中。在JFrame窗体上新建了一个带有颜色的JPanel,再在这个panel上面进行画线,这样呢就使得自己的棋盘变得~~美观些吧!
棋子的实现
下棋功能的实现需要考虑的地方也蛮多的:
1.首先想到下棋就是使用一个监听器来监听之前创建的panel棋盘,在鼠标释放的时候执行画园儿的操作。
2.怎么完成黑白交替着下
3.怎么使得棋子都下在正确的位置(网格线的相交点上)
4.怎么使得一个位置上只能存在一个棋子
啊~~我们再来一条一条的完善。
第一步很简单了,创建一个监听器来继承MouseAdapter这个抽象类。至于为什么不是实现MouseListener这个接口呢,原因很简单a~
因为实现MouseAdapter这个抽象类我们只需再重写我们需要用到的方法就可以了,而实现一个接口就要把他所有的抽象方法都要实现。这个五子棋的我们只用到的就是MouseReleased鼠标释放这一个,所以继承MouseAdapter显然更为简单。
然后重写其中MouseReleased方法,在鼠标释放的时候获取该点的xy坐标,在panel上获取画布:getGraphics(); 后就可以在上面画棋子了~~这样第一步也就完成了。
实现黑白交替呢~这里只需要一个控制变量,我使用的是一个boolean值state用来存储,true的时候表示该下黑子了,false的时候表示改下白子了。我们只需判断
if(state){
这样就完成了黑白子交替着下的功能~~
下一步是让棋子正位,我使用的方法是又自定义了一个坐标修正的函数。
* 下棋位置坐标修正的方法
public int correctXY(int x) {
x = x / 40;
return x * 40;
我就是用这样一个correctXY方法,在获取所点位置的xy坐标的时候进行一个修正,例如:
int x = correctXY(e.getX());
这样就把所获得到的点通过这个方法给修正了,看似好像除以四十又返回一个乘以四十好像没有变化,但这样是使得每一个获取到的坐标都是四十的倍数,也就是在正确的位置上。
下棋的最后一步就是使得一个点位只能下一个棋子,这个就是很简单了,只要我们定义一个二维数组,行列均为15,也就是这个棋盘的行列数,在每一个位置下棋后都在二维数组的对应位置中存入下的什么棋子,例如下的黑棋则在那个位置附上1,白子则附为-1。所以只要在下棋的时候不只只是判定state的true或者false,同时在判定所下位置二维数组是否为0,若不为0则说明该位置有棋子则不执行下棋操作。so easy~~~
这样我们就可以在这个棋盘上面下棋了~~
最后一步~就是判段输赢的方法了
使用的方法就是每在我们下棋的时候都应该判定一次,通过获得每次所下棋子的位置来向四周八个方向分别判断是否已经有五个棋子相连了。如果有则返回一个true。然后在用一个方法来当有判断五连的方法有返回true的话,就看当前点的棋子是什么颜色的,黑子的话就是黑子五连了,否则就是白子五连。
监听器中的所有代码都放在一起啦:
import java.awt.C
import java.awt.G
import java.awt.P
import java.awt.event.MouseA
import java.awt.event.MouseE
import java.util.R
import javax.swing.JP
public class WZQ_listener extends MouseAdapter {
* 设置黑白棋标识 true表示黑子,false表示白子
public static boolean state =
public int x,
public static String[][] array = new String[700][700];
public static int[][] array_win = new int[15][15];
public static int[][] array_pve = new int[15][15];
public static int count_
public static int count_where = 0;
public static R
public static L
* 重载他·的构造方法
public WZQ_listener(Graphics g) {
// this.panel =
* 鼠标释放执行的方法
public void mouseReleased(MouseEvent e) {
x = correctXY(e.getX());
y = correctXY(e.getY());
System.out.println("x:"+x+"
* 判定为人人对战
if (ActListener.GameModel == 1) {
if (x & 582 && x &= 0 && y & 582 && y &= 0) {
if (state && array[x][y] == null) {
g.setColor(Color.BLACK);
g.fillOval(x, y, WZQ_config.Chess_size,
WZQ_config.Chess_size);
array[x][y] = "black";
array_win[getXY(y)][getXY(x)] = 1;
} else if (array[x][y] == null) {
g.setColor(Color.WHITE);
g.fillOval(x, y, WZQ_config.Chess_size,
WZQ_config.Chess_size);
array[x][y] = "white";
array_win[getXY(y)][getXY(x)] = -1;
if (Win(getXY(y), getXY(x)) == 1) {
result = new Result(1);
result.initUI();
} else if (Win(getXY(y), getXY(x)) == -1) {
result = new Result(-1);
result.initUI();
for (int i = 0; i & 15; i++) {
for (int j = 0; j & 15; j++) {
System.out.print(array_win[i][j] + "
System.out.println("");
System.out.println("");
* 人机对战
else if (ActListener.GameModel == 2) {
if (x & 582 && x & 10 && y & 582 && y & 10 && array[x][y] == null) {
g.setColor(Color.BLACK);
g.fillOval(x - WZQ_config.Chess_size / 2, y
- WZQ_config.Chess_size / 2, WZQ_config.Chess_size,
WZQ_config.Chess_size);
array[x][y] = "black";
array_win[getXY(y)][getXY(x)] = 1;
array_pve[getXY(y)][getXY(x)] = 0;
for (int i = 0; i & 15; i++) {
for (int j = 0; j & 15; j++) {
System.out.print(array_pve[i][j] + "
System.out.println("");
System.out.println("");
* 下棋位置坐标修正的方法
public int correctXY(int x) {
x = x / 40;
return x * 40;
public int getXY(int x) {
x = x / 40;
* 判赢方法
* 判定横向五个相连
public boolean winRow(int row, int column) {
int count = 1;
for (int i = column + 1; i & 15; i++) {// 向右查找
if (array_win[row][column] == array_win[row][i]) {
for (int i = column - 1; i &= 0; i--) {// 向左查找
if (array_win[row][column] == array_win[row][i]) {
if (count &= 5) {
* 判定竖向五个相连
public boolean winColumn(int row, int column) {
int count = 1;
for (int i = row + 1; i & 15; i++) {// 向右查找
if (array_win[row][column] == array_win[i][column]) {
for (int i = row - 1; i &= 0; i--) {// 向左查找
if (array_win[row][column] == array_win[i][column]) {
if (count &= 5) {
* 判定斜向右下五个相连
public boolean winRightDown(int row, int column) {
int count = 1;
for (int i = column + 1, j = row + 1; i & 15 && j & 15; i++, j++) {// 向右查找
if (array_win[row][column] == array_win[j][i]) {
for (int i = column - 1, j = row - 1; i &= 0 && j &= 0; i--, j--) {// 向左查找
if (array_win[row][column] == array_win[j][i]) {
if (count &= 5) {
* 判定斜向左下五个相连
public boolean winLeftDown(int row, int column) {
int count = 1;
for (int i = column - 1, j = row + 1; i &=0 && j & 15; i--, j++) {// 向右查找
if (array_win[row][column] == array_win[j][i]) {
for (int i = column + 1, j = row - 1; i &15 && j &= 0; i++, j--) {// 向左查找
if (array_win[row][column] == array_win[j][i]) {
if (count &= 5) {
public int Win(int row, int column) {
if (winRow(row, column) || winColumn(row, column)
|| winRightDown(row, column) || winLeftDown(row, column)) {
if (array_win[row][column] == 1)
else if (array_win[row][column] == -1)
return -1;
最后还有一点可以完善的,就是我所做的是判断有五连之后又会弹出一个新的界面,上面提示某某子五连,某某子获得胜利。同时提供两个按钮选择重新开始或者退出。~
import java.awt.BorderL
import java.awt.D
import java.awt.FlowL
import java.awt.event.ActionE
import java.awt.event.ActionL
import java.awt.event.MouseA
import java.awt.event.MouseE
import javax.swing.AbstractB
import javax.swing.JB
import javax.swing.JF
import javax.swing.JL
import javax.swing.JP
public class Result extends JFrame{
public Result(int i){
* 定义一个生成界面的方法
public void initUI(){
this.setTitle("结果");
this.setSize(new Dimension(400,200));
this.setLocationRelativeTo(null);
this.setResizable(false);
this.setLayout(new BorderLayout());
this.setDefaultCloseOperation(HIDE_ON_CLOSE);
panel = new JPanel();
panel.setLayout(new FlowLayout());
this.add(panel,BorderLayout.CENTER);
if(i == 1){
JLabel lab = new JLabel("黑子五连,黑子胜!");
panel.add(lab,BorderLayout.CENTER);
else if(i == -1){
JLabel lab = new JLabel("白子五连,白子胜!");
panel.add(lab);
JPanel pal = new JPanel();
JButton btn_restart = new JButton("重新开始");
JButton btn_exit = new JButton("退出游戏");
btn_restart.setActionCommand("restart");
btn_exit.setActionCommand("exit");
ActListener al = new ActListener();
btn_restart.addActionListener(al);
btn_exit.addActionListener(al);
btn_restart.addMouseListener(al);
btn_exit.addMouseListener(al);
pal.setLayout(new FlowLayout());
this.add(pal,BorderLayout.SOUTH);
pal.add(btn_restart);
pal.add(btn_exit);
this.setVisible(true);
这样,这个人人对战的五子棋可以说是就完成了。~~人机的之后会在完善的!
有缺点不足麻烦指出~~#^_^。谢谢各位看的盆友~~~~~
最后附一张效果图哈:
浏览 19971
不错,很好
~~嘿。谢谢谢谢~
浏览: 36405 次
EastStone 写道不错,很好
~~嘿。谢谢谢谢~
不错,很好
版主太强了,写的很详细,思路很清晰,方便学习
ZaneLee007 写道java有现成的借口,何必非要自己做 ...
chinahker 写道哥,你冒泡排序都没写对还说了这么多。第 ...
(window.slotbydup=window.slotbydup || []).push({
id: '4773203',
container: s,
size: '200,200',
display: 'inlay-fix'java使用二维数组开发五子棋
java使用二维数组开发五子棋
主要使用到的技术:java基础语法java面向对象思想java数组,二维数组java异常处理主要步骤和思路:1,制作一个棋盘类。棋盘类里面有行属性,列属性,二维数组属性。有一个打印棋盘的方法。做一个测试类,先打印出棋盘。利用二维数组先打印出棋盘2,制作一个下棋类。1》将棋盘类放入该类,作为属性。因为要用到棋盘。2》游戏开始方法start()。首先是玩家1下棋,利用键盘输入,将玩家1的棋子放入棋盘。下完之后打印出棋盘3》当玩家1下完之后,轮到玩家2下棋。这里要有一个判断的方法。4》将玩家2的棋子放入棋盘,其实就是玩家1放棋子的代码。3,将棋子放好之后,就需要看棋盘是否连成线了。1》写四个方法,返回boolean。每个方法连成一线。四个方向连成线。横,竖,左斜,右斜。算法:循环遍历棋子所在位置的前面四个和后面四个坐标,如果是连着的,说明五子连珠了。4,在start()方法里面加代码,如果玩家1已经连成线了,那么提示玩家1已经赢了,跳出游戏。5,注意,还需要判断玩家放棋子的时候,是否已经超出棋盘的边界,是否该坐标已经有棋子。这里抛出异常信息。下面公布代码:首先是代码结构。图中有棋盘类,棋盘计算类,测试类,自定义异常类。Test.java 测试运行类QipanCalc .java 棋盘计算类Qipan.java 棋盘类WzqException.java 自定义异常类可以照着打一遍理解。主要是在横着,竖着,斜着的五颗棋子是否连成线。关键算法。测试不够多,如有发现bug,请留言!谢谢。
本文仅代表作者观点,不代表百度立场。系作者授权百家号发表,未经许可不得转载。
百家号 最近更新:
简介: 一个软件工程师的自我修养,程序中有你,程序中有我。
作者最新文章2012年2月 Java大版内专家分月排行榜第三2011年8月 Java大版内专家分月排行榜第三2011年6月 Java大版内专家分月排行榜第三2011年4月 Java大版内专家分月排行榜第三2010年12月 Java大版内专家分月排行榜第三
2012年2月 Java大版内专家分月排行榜第三2011年8月 Java大版内专家分月排行榜第三2011年6月 Java大版内专家分月排行榜第三2011年4月 Java大版内专家分月排行榜第三2010年12月 Java大版内专家分月排行榜第三
2012年2月 Java大版内专家分月排行榜第三2011年8月 Java大版内专家分月排行榜第三2011年6月 Java大版内专家分月排行榜第三2011年4月 Java大版内专家分月排行榜第三2010年12月 Java大版内专家分月排行榜第三
本帖子已过去太久远了,不再提供回复功能。博客分类:
五子棋算是我学习java一个月以来第一次做的一个项目,也算是小游戏。开始觉得五子棋遥不可及,后来在老师的指导下也一步步攻克难关,做了出来。
首先是最初的界面实现。用一个再寻常不过的JFrame窗体,并常规的设置属性。
不过在勾画棋盘时,我们第一次用到了对界面的重绘。代码是public void paint (Graphics g){}这个方法是重写原来默认的JFrame自带paint方法,在此方法中用循环的方式,画出一条条线,并需要精确计算,以保证能画出15*15的棋盘。当然重绘的不仅只有棋盘而已,在后来每下一个棋子,在最小化JFrame窗体界面后又会这些下的棋子会自动消失,这时就需要我们用重绘的方法将它们一一画出来。这个代码实现就相对难一些,后面再讨论。
接下来是画棋子,这里自然免不了添加MouseListener监听器。在Released操作中,在每次释放鼠标后便要在释放的位置最近的那个点画出一个棋子。我起初觉得这是一件很困难的事,并尝试用取余的方法分了四种情况一一讨论,也实现了目标。不过,在老师的指导下,我引入了行和列的关系,巧妙的给坐标加上20以后不用取余,得到我需要的行数和列数,进而画出想要的位置的棋子。而引入行数和列数,自然需要构建对接下来的事件很有必要的数组。因为棋盘和行列之分。所以只要构建两个变量相组合便能方便地记录棋盘上的每一个位置,而再没有比二维数组更有效的方式。
有了数组,除了实现画棋子,在前面提到了重绘方法上,也变得容易了,只要把画的棋子所对应的数组的位置传到前面,那么就能简单地画出每一个画过的棋子,并保存。除此以外,给画过黑棋和白棋的位置所对应的数组分别赋上一个值,这样也方便能在画过的地方不再重画。然后,采用计数器或者时间真假的方法,用循环的方式,来规定一次下黑棋一次下白棋。
最后,也是最难的地方,便是五子棋判断输赢的部分。起初觉得好像这部分的实现遥不可及。可仔细想想,五子棋判断输赢的方式也很简单啊。无非是有没有五个相同颜色的棋子横向或竖向或斜向连在一起。于是,在定义数组后这显得很简单了,我单独定义一个类用以判断输赢,每下一个棋子,就判断这个棋子在横向、竖向和两个斜向上是否有五子连在一起,然后调用这四个方向的判断方法,最终完成了判断输赢方法的编写。然后,在继承MouseListener的类中,下完棋子后,调用这个方法,以此判断输赢。最后,人人版的五子棋便大功告成了。
旧琴房时光
浏览: 3727 次
大几?好好学啊
(window.slotbydup=window.slotbydup || []).push({
id: '4773203',
container: s,
size: '200,200',
display: 'inlay-fix'

我要回帖

更多关于 java二维数组五子棋 的文章

 

随机推荐