《Java基本功练习九》讲到了五子棋,并且提出了改进的建议。相信大家都掌握了多维数组的相关操作,上一篇提到了检测输赢方法有两种:1)每下一颗棋子就遍历棋盘;2)每下一颗棋子,判断其周围的情况来确定输赢。
本篇博文就以悬挂的四子棋作为例子,来讲述2)中的判定方法,由于只需判定当前所下棋子的情况,而不用遍历棋盘,所以效率更高。
悬挂的四子棋,又叫连接四子,相信大家小时候都玩过把。它是一个两个人玩的棋盘游戏,在游戏中,玩家轮流将有颜色的棋子放在一个六行七列的垂直悬挂的网格中,如下所示:
这个游戏的目的是在反方出现一行、一列或者一对角线上有四个相同颜色的棋子之前,正方能先做到。程序提示两个玩家交替的下红字Red或黄子Yellow。当丢下一子时,程序在控制台重新显示这个棋盘,然后确定游戏的状态(赢、平局还是继续)。运行效果如下图所示(只上传了前两张和后两张):
设计此题的时候需要考虑几个问题:1)如何模拟下子时只能下到每列的最下端的空位处;
2)如果某一列满了,继续往该列下子要报错并提示重新输入;
3)怎么设计判断方法,从而只需判断当前所下子的情况以确定胜负;
4)怎么判断平局
5)棋盘怎么刷新
设计的时候可以自己先把每步的情况考虑清楚,如何用代码去实现,在纸上打个草稿,然后再开始写代码,并且每实现一个小的步骤都运行看看结果是否正确,正确之后再继续往下设计,这样可以减轻调试的负担,降低调试的难度,切记!
以下是实现的源代码:
package MutiArrays;
import java.util.Scanner;
public class practice7Arrays{
//悬挂的四子棋
public static void main(String[]args){
Scanner input = new Scanner(System.in);
String[][] qi = new String[6][7];
String yuanShiYuanSu = "| ";
String yellow = "| Y ";
String red = "| R ";
int count = 0;//谁下子及下了多少子的判断计数器
//初始化棋子数组
for(int i = 0;i < qi.length;i++)
for(int j = 0;j < qi[0].length;j++)
qi[i][j] = yuanShiYuanSu;
//画出原始棋盘
System.out.println("-----------------------------");
for(int i = qi.length - 1;i >= 0;i--){
for(int j = 0;j < qi[0].length;j++)
System.out.print(qi[i][j]);
System.out.println("|");
System.out.println("-----------------------------");
}
for(int i = 0;i < qi[0].length;i++)
System.out.print("* "+(i+1)+" ");
System.out.println("*");
int row = 0,column = 0;//行列下标初始化
//下棋循环开始
while (true) {
row = 0;
column = 0;
if (count % 2 == 0) {//黄方下子
System.out.print("\n\nY player please drop a yellow disk at column(1~7):");
while (true) {//黄方下子循环开始
column = input.nextInt() - 1;
if (column >= 0 && column <= 6) {// 输入合法进行下子
for (row = 0; row < qi.length; row++) {
if (qi[row][column] == yuanShiYuanSu) {
qi[row][column] = yellow;
break;
}
}
if (row == qi.length)//该列棋子满,重新输入
System.out.print("The column of you enter is full,"
+ "please reEnter! : ");
else//棋子没满,下子结束
break;
}
else// 输入不合法,重新下子
System.out.print("You enter the wrong column,"
+ "please reEnter! : ");
}//黄方下子循环结束
}//if(count % 2 == 0)
else{//红方下子
System.out.print("\n\nR player please drop a yellow disk at column(1~7):");
while (true) {//红方下子循环开始
column = input.nextInt() - 1;
if (column >= 0 && column <= 6) {// 输入合法进行下子
for (row = 0; row < qi.length; row++) {
if (qi[row][column] == yuanShiYuanSu) {
qi[row][column] = red;
break;
}
}
if (row == qi.length)//该列棋子满,重新输入
System.out.print("The column of you enter is full,"
+ "please reEnter! : ");
else//棋子没满,下子结束
break;
}
else// 输入不合法,重新下子
System.out.print("You enter the wrong column,"
+ "please reEnter! : ");
}//红方下子循环结束
}//if(count % 2 != 0)
//画出棋盘
System.out.println("-----------------------------");
for(int i = qi.length - 1;i >= 0;i--){
for(int j = 0;j < qi[0].length;j++)
System.out.print(qi[i][j]);
System.out.println("|");
System.out.println("-----------------------------");
}
for(int i = 0;i < qi[0].length;i++)
System.out.print("* "+(i+1)+" ");
System.out.println("*");
//输赢标志位
boolean flagForYWin = false;
boolean flagForRWin = false;
//只需对当前下子的周围情况进行判断来决定棋局结果
if (count % 2 == 0) {//yellow player is win?
//行检测开始
if (column <= 3) {
for (int jj = 0; jj <= column; jj++)
if (qi[row][jj] == yellow
&& qi[row][jj + 1] == yellow
&& qi[row][jj + 2] == yellow
&& qi[row][jj + 3] == yellow) {
flagForYWin = true;
break;
}
}
else {
for (int jj = column - 3; jj <= 3; jj++)
if (qi[row][jj] == yellow
&& qi[row][jj + 1] == yellow
&& qi[row][jj + 2] == yellow
&& qi[row][jj + 3] == yellow) {
flagForYWin = true;
break;
}
}
if (flagForYWin) {
System.out.println("The yellow player win the game!");
break;
}
//列检测开始
if (row >= 3) {
if (qi[row][column] == yellow
&& qi[row - 1][column] == yellow
&& qi[row - 2][column] == yellow
&& qi[row - 3][column] == yellow)
flagForYWin = true;
}
if (flagForYWin) {
System.out.println("The yellow player win the game!");
break;
}
//正反对角检测
if(row >= 3){
if(column < 3){
if (qi[row][column] == yellow
&& qi[row - 1][column + 1] == yellow
&& qi[row - 2][column + 2] == yellow
&& qi[row - 3][column + 3] == yellow)
flagForYWin = true;
}
else if(column > 3){
if (qi[row][column] == yellow
&& qi[row - 1][column - 1] == yellow
&& qi[row - 2][column - 2] == yellow
&& qi[row - 3][column - 3] == yellow)
flagForYWin = true;
}
else{
if ((qi[row][column] == yellow
&& qi[row - 1][column + 1] == yellow
&& qi[row - 2][column + 2] == yellow
&& qi[row - 3][column + 3] == yellow)
|| (qi[row][column] == yellow
&& qi[row - 1][column - 1] == yellow
&& qi[row - 2][column - 2] == yellow
&& qi[row - 3][column - 3] == yellow))
flagForYWin = true;
}
}
if (flagForYWin) {
System.out.println("The yellow player win the game!");
break;
}
}//yellow player is win?
else{//red player is win?
//行检测开始
if (column <= 3) {
for (int jj = 0; jj <= column; jj++)
if (qi[row][jj] == red
&& qi[row][jj + 1] == red
&& qi[row][jj + 2] == red
&& qi[row][jj + 3] == red) {
flagForRWin = true;
break;
}
}
else {
for (int jj = column - 3; jj <= 3; jj++)
if (qi[row][jj] == red
&& qi[row][jj + 1] == red
&& qi[row][jj + 2] == red
&& qi[row][jj + 3] == red) {
flagForRWin = true;
break;
}
}
if (flagForRWin) {
System.out.println("The red player win the game!");
break;
}
//列检测开始
if (row >= 3) {
if (qi[row][column] == red
&& qi[row - 1][column] == red
&& qi[row - 2][column] == red
&& qi[row - 3][column] == red)
flagForRWin = true;
}
if (flagForRWin) {
System.out.println("The red player win the game!");
break;
}
//正反对角检测
if(row >= 3){
if(column < 3){
if (qi[row][column] == red
&& qi[row - 1][column + 1] == red
&& qi[row - 2][column + 2] == red
&& qi[row - 3][column + 3] == red)
flagForRWin = true;
}
else if(column > 3){
if (qi[row][column] == red
&& qi[row - 1][column - 1] == red
&& qi[row - 2][column - 2] == red
&& qi[row - 3][column - 3] == red)
flagForRWin = true;
}
else{
if ((qi[row][column] == red
&& qi[row - 1][column + 1] == red
&& qi[row - 2][column + 2] == red
&& qi[row - 3][column + 3] == red)
|| (qi[row][column] == red
&& qi[row - 1][column - 1] == red
&& qi[row - 2][column - 2] == red
&& qi[row - 3][column - 3] == red))
flagForRWin = true;
}
}
if (flagForRWin) {
System.out.println("The red player win the game!");
break;
}
}
count++;//棋子数加1,并用于谁下棋子的判断
//棋盘下满棋子,是平局
if(count == 6*7){
System.out.println("棋盘棋子已经下满,是平局!");
break;
}
}//下棋循环结束
}//方法块
}//类块