题目:
井字游戏
设计一个算法,判断玩家是否赢了井字游戏。输入是一个 N x N 的数组棋盘,由字符" ","X"和"O"组成,其中字符" "代表一个空位。
以下是井字游戏的规则:
玩家轮流将字符放入空位(" ")中。
第一个玩家总是放字符"O",且第二个玩家总是放字符"X"。
"X"和"O"只允许放置在空位中,不允许对已放有字符的位置进行填充。
当有N个相同(且非空)的字符填充任何行、列或对角线时,游戏结束,对应该字符的玩家获胜。
当所有位置非空时,也算为游戏结束。
如果游戏结束,玩家不允许再放置字符。
如果游戏存在获胜者,就返回该游戏的获胜者使用的字符("X"或"O");如果游戏以平局结束,则返回 "Draw";如果仍会有行动(游戏未结束),则返回 "Pending"。
示例 1:
输入: board = ["O X"," XO","X O"]
输出: "X"
示例 2:
输入: board = ["OOX","XXO","OXO"]
输出: "Draw"
解释: 没有玩家获胜且不存在空位
示例 3:
输入: board = ["OOX","XXO","OX "]
输出: "Pending"
解释: 没有玩家获胜且仍存在空位
提示:
这个题目时对对战双发的战时瞬态做一个分析。
大家一定要注意审题,只存在以下四种情况
行
列
左对角线,题目说的是对角线,不是任何一条斜着的连线哦。 请一定注意,#字游戏是往格子里面放棋子,不是线上,对角线的个数也是n,不会玩的,可以先完两把,业务不熟练,危害不浅。我就想的复杂了。
右对角线,题目说的是对角线,不是任何一条斜着的连线哦。
思路:**求值法**,行列斜相同形状int值相加,如果等于*n的值,说明胜利,另外设置一个flag,存放是否空位,else就是Pendding了。
另外要特别注意,传入的是一个String类型的一维数组。
1.代码如下 Tictactoe.java:
package com.yuhl.right.leetcode;
/**
* @author yuhl
* @Date 2020/10/25 7:39
* @Classname Tictactoe
* @Description
* 井字游戏
* 设计一个算法,判断玩家是否赢了井字游戏。输入是一个 N x N 的数组棋盘,由字符" ","X"和"O"组成,其中字符" "代表一个空位。
*
* 以下是井字游戏的规则:
* 玩家轮流将字符放入空位(" ")中。
* 第一个玩家总是放字符"O",且第二个玩家总是放字符"X"。
* "X"和"O"只允许放置在空位中,不允许对已放有字符的位置进行填充。
* 当有N个相同(且非空)的字符填充任何行、列或对角线时,游戏结束,对应该字符的玩家获胜。
* 当所有位置非空时,也算为游戏结束。
* 如果游戏结束,玩家不允许再放置字符。
* 如果游戏存在获胜者,就返回该游戏的获胜者使用的字符("X"或"O");如果游戏以平局结束,则返回 "Draw";如果仍会有行动(游戏未结束),则返回 "Pending"。
*
* 示例 1:
* 输入: board = ["O X"," XO","X O"]
* 输出: "X"
*
* 示例 2:
* 输入: board = ["OOX","XXO","OXO"]
* 输出: "Draw"
* 解释: 没有玩家获胜且不存在空位
*
* 示例 3:
* 输入: board = ["OOX","XXO","OX "]
* 输出: "Pending"
* 解释: 没有玩家获胜且仍存在空位
*
* 提示:
* 1 <= board.length == board[i].length <= 100
* 输入一定遵循井字棋规则
*/
public class Tictactoe {
public static void main(String[] args) {
String[] boad = {"O X"," XO","X O"};
// String[] boad = {"OOX","XXO","OXO"};
// String[] boad = {"OOX","XXO","OX "};
String tictactoe = tictactoe(boad);
System.out.println(tictactoe);
}
public static String tictactoe(String[] board) {
//这个题目时对对战双发的战时瞬态做一个分析。
//大家一定要注意审题,只存在以下四种情况
//行
//列
//左对角线,题目说的是对角线,不是任何一条斜着的连线哦。 请一定注意,#字游戏是往格子里面放棋子,不是线上,对角线的个数也是n,不会玩的,可以先完两把,业务不熟练,危害不浅。我就想的复杂了。
//右对角线,题目说的是对角线,不是任何一条斜着的连线哦。
//
//总体思路:求值法,行列斜相同形状int值相加,如果等于*n的值,说明胜利,另外设置一个flag,存放是否空位,else就是Pendding了。
//另外要特别注意,传入的是一个String类型的一维数组。
int heng ;// 记录横的和值, 局部变量必须先赋值再使用哦!
int zong ;//记录纵的和值
int left = 0;//记录左撇的和值
int right = 0;//记录右捺的和值
boolean includeempty = false;//含有空格,默认位没有,false
int length = board.length;//记录字符串数组的长度
for(int i=0;i<length;i++){
heng = 0;//记录第0行(习惯,也就是第0行的总和,第二次的话就是第0行的总和,便于理解)
zong = 0;//记录第0列(习惯,也就是第1列的总和,第二次的话就是第1列的总和,便于理解)
for(int j=0; j<length; j++){
heng += (int)board[i].charAt(j);//把第0行,第0列的元素给heng,之后是第0行,第1列;之后是第0行第2列... ...
zong += (int)board[j].charAt(i);//把第0列,第0行的元素给zong,之后是第1列,第0行;之后是第2列第0行... ...
if(board[i].charAt(j) == ' ') includeempty = true;//如果含有一个空格,则标注含有空格。 每一个位置均有走过。
}
//至此,第i行列的综合出来了。做个判断,如果有胜出的就停止。如果有位空的就更新includeempty位true
if((heng == (int)'X' * length) || (zong == (int)'X' *length)) return "X";//如果横或者纵全为X,则返回X,停止程序 解释:如果整行或者整列位同一个字符,则正好满足等式。
if((heng == (int)'O' * length) || (zong == (int)'O' *length)) return "O";//如果横或者纵全为O,则返回O,停止程序
//左撇的和
left += (int)board[i].charAt(i);
//右捺的和
right += (int)board[i].charAt(length-i-1);
}
//位层for循环结束后左撇和右捺的和计算完毕,可以做判断了。
if((left == (int)'X' * length) || (right == (int)'X' *length)) return "X";
if((left == (int)'O' * length) || (right == (int)'O' *length)) return "O";
if(includeempty == true) return "Pending";
return "Draw";
}
}
2.执行结果:
"C:\Program Files\Java\jdk1.8.0_201\bin\java.exe"
X