package org.crazyit.gobang; /** * 棋盘对象 */ public class Chessboard { // 定义一个二维数组来充当棋盘 private String[][] board; // 定义棋盘的大小 public static final int BOARD_SIZE = 22; /** * 初始化棋盘 * * @return void */ public void initBoard() { // 初始化棋盘数组 board = new String[BOARD_SIZE][BOARD_SIZE]; // 把每个元素赋值为“十”,用于控制台输出棋盘 for (int i = 0; i < BOARD_SIZE; i++) { for (int j = 0; j < BOARD_SIZE; j++) { board[i][j] = "十"; } } } public void test() { Object[][] array = new Object[10][10]; for (int i = 0; i < array.length; i++) { for (int j = 0; j < array[i].length; j++) { array[i][j] = new Object(); } } } /** * 在控制台输出棋盘的方法 */ public void printBoard() { // 打印每个数组元素 for (int i = 0; i < BOARD_SIZE; i++) { for (int j = 0; j < BOARD_SIZE; j++) { // 打印后不换行 System.out.print(board[i][j]); } // 每打印完一行数组元素就换行一次 System.out.print("\n"); } } /** * 给棋盘位置赋值 * * @param posX * X坐标 * @param posY * Y坐标 * @param chessman * 棋子 */ public void setBoard(int posX, int posY, String chessman) { this.board[posX][posY] = chessman; } /** * 返回棋盘 * * @return 返回棋盘 */ public String[][] getBoard() { return this.board; } }
*********************************************************************************
package org.crazyit.gobang; /** * 棋子枚举类 */ public enum Chessman { BLACK("●"), WHITE("○"); private String chessman; /** * 私有构造器 */ private Chessman(String chessman) { this.chessman = chessman; } /** * @return String 黑棋或者白棋 */ public String getChessman() { return this.chessman; } }
*********************************************************************************
package org.crazyit.gobang; import java.io.BufferedReader; import java.io.InputStreamReader; /** * 五子棋游戏类 */ public class GobangGame { // 定义达到赢条件的棋子数目 private final int WIN_COUNT = 5; // 定义用户输入的X坐标 private int posX = 0; // 定义用户输入的X坐标 private int posY = 0; // 定义棋盘 private Chessboard chessboard; /** * 空构造器 */ public GobangGame() { } /** * 构造器,初始化棋盘和棋子属性 * * @param chessboard * 棋盘类 */ public GobangGame(Chessboard chessboard) { this.chessboard = chessboard; } /** * 检查输入是否合法。 * * @param inputStr * 由控制台输入的字符串。 * @return 字符串合法返回true,反则返回false。 */ public boolean isValid(String inputStr) { // 将用户输入的字符串以逗号(,)作为分隔,分隔成两个字符串 String[] posStrArr = inputStr.split(","); try { posX = Integer.parseInt(posStrArr[0]) - 1; posY = Integer.parseInt(posStrArr[1]) - 1; } catch (NumberFormatException e) { chessboard.printBoard(); System.out.println("请以(数字,数字)的格式输入:"); return false; } // 检查输入数值是否在范围之内 if (posX < 0 || posX >= Chessboard.BOARD_SIZE || posY < 0 || posY >= Chessboard.BOARD_SIZE) { chessboard.printBoard(); System.out.println("X与Y坐标只能大于等于1,与小于等于" + Chessboard.BOARD_SIZE + ",请重新输入:"); return false; } // 检查输入的位置是否已经有棋子 String[][] board = chessboard.getBoard(); if (board[posX][posY] != "十") { chessboard.printBoard(); System.out.println("此位置已经有棋子,请重新输入:"); return false; } return true; } /** * 开始下棋 */ public void start() throws Exception { // true为游戏结束 boolean isOver = false; chessboard.initBoard(); chessboard.printBoard(); // 获取键盘的输入 BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); String inputStr = null; // br.readLine:每当键盘输入一行内容按回车键,则输入的内容被br读取到 while ((inputStr = br.readLine()) != null) { isOver = false; if (!isValid(inputStr)) { // 如果不合法,要求重新输入,再继续 continue; } // 把对应的数组元素赋为"●" String chessman = Chessman.BLACK.getChessman(); chessboard.setBoard(posX, posY, chessman); // 判断用户是否赢了 if (isWon(posX, posY, chessman)) { isOver = true; } else { // 计算机随机选择位置坐标 int[] computerPosArr = computerDo(); chessman = Chessman.WHITE.getChessman(); chessboard.setBoard(computerPosArr[0], computerPosArr[1], chessman); // 判断计算机是否赢了 if (isWon(computerPosArr[0], computerPosArr[1], chessman)) { isOver = true; } } // 如果产生胜者,询问用户是否继续游戏 if (isOver) { // 如果继续,重新初始化棋盘,继续游戏 if (isReplay(chessman)) { chessboard.initBoard(); chessboard.printBoard(); continue; } // 如果不继续,退出程序 break; } chessboard.printBoard(); System.out.println("请输入您下棋的坐标,应以x,y的格式输入:"); } } /** * 是否重新开始下棋。 * * @param chessman * "●"为用户,"○"为计算机。 * @return 开始返回true,反则返回false。 */ public boolean isReplay(String chessman) throws Exception { chessboard.printBoard(); String message = chessman.equals(Chessman.BLACK.getChessman()) ? "恭喜您,您赢了," : "很遗憾,您输了,"; System.out.println(message + "再下一局?(y/n)"); BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); if (br.readLine().equals("y")) { // 开始新一局 return true; } return false; } /** * 计算机随机下棋 */ public int[] computerDo() { int posX = (int) (Math.random() * (Chessboard.BOARD_SIZE - 1)); int posY = (int) (Math.random() * (Chessboard.BOARD_SIZE - 1)); String[][] board = chessboard.getBoard(); while (board[posX][posY] != "十") { posX = (int) (Math.random() * (Chessboard.BOARD_SIZE - 1)); posY = (int) (Math.random() * (Chessboard.BOARD_SIZE - 1)); } int[] result = { posX, posY }; return result; } /** * 判断输赢 * * @param posX * 棋子的X坐标。 * @param posY * 棋子的Y坐标 * @param ico * 棋子类型 * @return 如果有五颗相邻棋子连成一条直接,返回真,否则相反。 */ public boolean isWon(int posX, int posY, String ico) { // 直线起点的X坐标 int startX = 0; // 直线起点Y坐标 int startY = 0; // 直线结束X坐标 int endX = Chessboard.BOARD_SIZE - 1; // 直线结束Y坐标 int endY = endX; // 同条直线上相邻棋子累积数 int sameCount = 0; int temp = 0; // 计算起点的最小X坐标与Y坐标 temp = posX - WIN_COUNT + 1; startX = temp < 0 ? 0 : temp; temp = posY - WIN_COUNT + 1; startY = temp < 0 ? 0 : temp; // 计算终点的最大X坐标与Y坐标 temp = posX + WIN_COUNT - 1; endX = temp > Chessboard.BOARD_SIZE - 1 ? Chessboard.BOARD_SIZE - 1 : temp; temp = posY + WIN_COUNT - 1; endY = temp > Chessboard.BOARD_SIZE - 1 ? Chessboard.BOARD_SIZE - 1 : temp; // 从左到右方向计算相同相邻棋子的数目 String[][] board = chessboard.getBoard(); for (int i = startY; i < endY; i++) { if (board[posX][i] == ico && board[posX][i + 1] == ico) { sameCount++; } else if (sameCount != WIN_COUNT - 1) { sameCount = 0; } } if (sameCount == 0) { // 从上到下计算相同相邻棋子的数目 for (int i = startX; i < endX; i++) { if (board[i][posY] == ico && board[i + 1][posY] == ico) { sameCount++; } else if (sameCount != WIN_COUNT - 1) { sameCount = 0; } } } if (sameCount == 0) { // 从左上到右下计算相同相邻棋子的数目 int j = startY; for (int i = startX; i < endX; i++) { if (j < endY) { if (board[i][j] == ico && board[i + 1][j + 1] == ico) { sameCount++; } else if (sameCount != WIN_COUNT - 1) { sameCount = 0; } j++; } } } return sameCount == WIN_COUNT - 1 ? true : false; } public static void main(String[] args) throws Exception { GobangGame gb = new GobangGame(new Chessboard()); gb.start(); } }
运行效果图:
资源与学习共享下: