基于前几次的基础知识,比如数组,构造方法,循环,选择等等知识的练习 ,今天我们来做一个综合性的练习题—五子棋游戏!!!
前述:首先,拿到这个题,我们需要逐层剖析,由浅入深,将复杂问题简单化,当然,所有的编程题一样,一步一步,功能模块化,所有问题也就游刃而解。。
ps:此游戏中涉及到了我们之前未涉及到的全局变量,全局变量呢,格式就是将其定义为与主函数main平级。全局变量有这两个有点:①全局可视,任何一个函数都可以访问和更改变量值。②内存地址固定,读写效率高。
下面我们对其逐步剖析并解决:
- 1、下棋游戏,我们必须先有棋盘,所以必须先创建棋盘,也就是构造一个方法来定义并初始化我们需要的棋盘例如:initBoard()
- 2、定义好了之后,当然也需要将其显示出来供玩家play,这里构造一个方法来打印棋盘(棋盘可以用字符“+”构成,当然大家有更好的也可以用)例如:printBoard()
- 3、上面可以说是下棋的准备工作,准备做好之后呢,我们也就可以开始下棋了。例如:startGame()
- 4,上述就是下棋的大框架,核心思路在startGame()中,其中我们要将游戏结束(这里不考虑和棋)的条件写出来,例如:isgameOver() 当然,这也是关键所在的函数,下面我们详述isgameOver()函数,首先,思路图献上:
解析上图:
1、创建的这个15×15的棋盘中,要想结束这个游戏,就必须要有一方获胜,获胜的条件就是上、下、左、右、右上、右下、左下、左上八个方向有任意一个方向存在连续5个相同颜色的棋子即可结束此轮游戏。但是我遍历每个棋子四个方向的连续性即可涵盖上述八个方向,这里举例这四个方向:向右、向下、右下、右上(应该可以看懂原因)。
2、上图中我将短直线(或短直线上带一个圆圈)命名为标杆,每个标杆颜色对应着一个矩形范围(遍历该范围中的每个棋子)。方便下面叙述:①向右(红色):红色矩形框是标杆遍历棋盘的临界范围,即列数j<11
②向下(绿色):绿色矩形框是标杆遍历棋盘的临界范围,即行数i<11
③右下(黄色):黄色矩形框是标杆遍历棋盘的临界范围,即行数i<11&&列数j<11
④右上(蓝色):蓝色矩形框是标杆遍历棋盘的临界范围,即行数i>3&&列数j<11
综上 :代码 奉上。。
import java.util.*;
class WuZiQi{
/**
问题:五子棋游戏
*/
public static String[][] board=null;
public static Scanner scanner=new Scanner(System.in);
public static void main(String[] args){
//1,定义并初始化棋盘
initBoard();
//2,打印棋盘
printBoard();
//3,开始下棋
startGame();
}
public static void startGame(){
int player=0;
while(!isgameOver()){
if(player%2==0){
System.out.println(">>>黑方下棋:");
if(!xiaqi("O")){
continue;
}
}else{
System.out.println(">>>白方下棋:");
if(!xiaqi("X")){
continue;
}
}
player++;
}
System.out.print("Game Over!");
if(player%2==1){
System.out.print("黑方胜!");
}
else{
System.out.print("白方胜!");
}
}
public static boolean isgameOver(){
for(int i=0;i<board.length;i++){
for(int j=0;j<board[i].length;j++){
if(!board[i][j].equals("+")){ //遍历的是棋子
//向右
if(j<11){
boolean flag=true;
for(int dy=1;dy<=4;dy++){//dy为该方向的偏移
if(board[i][j]!=board[i][j+dy]){
flag=false;
break;
}
}
if(flag){//对退出循环的两种循环进行区别
return true;
}
}//此次向右遍历并不能结束,还需判断其他三个方向
//向下
if(i<11){
boolean flag=true;
for(int dx=1;dx<=4;dx++){
if(board[i][j]!=board[i+dx][j]){
flag=false;
break;
}
}
if(flag){
return true;
}
}
//右下
if(j<11&&i<11){
boolean flag=true;
for(int d=1;d<=4;d++){
if(board[i][j]!=board[i+d][j+d]){
flag=false;
break;
}
}
if(flag){
return true;
}
}
//右上
if(i>3&&j<11){
boolean flag=true;
for(int d=1;d<=4;d++){
if(board[i][j]!=board[i-d][j+d]){
flag=false;
break;
}
}
if(flag){
return true;
}
}
}
}
}
return false;//都没有满足游戏结束条件,那就继续下棋
}
public static boolean xiaqi(String chess){
System.out.print("请输入x坐标:");
int x=scanner.nextInt()-1;
System.out.print("请输入y坐标:");
int y=scanner.nextInt()-1;
if(board[x][y].equals("+")){
board[x][y]=chess;
printBoard();
return true;
}else{
System.out.println(">>>棋子已存在,请重新下棋:");
return false;
}
}
public static void printBoard(){
System.out.print(" ");
for(int i=1;i<=15;i++){
System.out.printf("%-3d",i);
}
System.out.println();
for(int i=0;i<board.length;i++){
System.out.printf("%-3d",i+1);
for(int j=0;j<board[i].length;j++){
System.out.print(board[i][j]+" ");
}
System.out.println();
}
}
public static void initBoard(){
board=new String[15][15];
for(int i=0;i<board.length;i++){
for(int j=0;j<board[i].length;j++){
board[i][j]="+";
}
}
}
}
感谢各位提出宝贵意见!!!