Valid Sudoku
Determine if a Sudoku is valid, according to: Sudoku Puzzles - The Rules.
The Sudoku board could be partially filled, where empty cells are filled with the character '.'
.
A partially filled sudoku which is valid.
Note:
A valid Sudoku board (partially filled) is not necessarily solvable. Only the filled cells need to be validated.
解题思路:本题即为判断是否满足数独的三个条件,每一行每一列以及每个3X3粗线宫中没有1-9的重复元素。
这个题的难度在leetcode里面是easy,也就是说,稍有常识的人都会想到一个算法,暴力法,通过遍历完成。我开始也这么想,但并没有这么做,经过仔细思考并看了其他大神的做法,学到了一个O(n^2)的算法,行列宫的判断算法。这里的行和列都比较容易,就是判断每行的对应元素是否重复。而宫的判断比较复杂,要求利用现有的行和列下标判断出属于对应的子矩阵。对于一个3X3的子矩阵来说,有如下二元函数满足判断条件,T=i-i%3+j/3.该函数可以推广到任意大小的子矩阵。上述T则对应子矩阵的序号。这个做法实在是太精妙了,但是我想不出这个二元函数的正确性的证明。。。
代码如下:
public boolean isValidSudoku(char[][] board) {
//每一行每一列每一宫都有数字且不重复 由此设置三个数组来判断
boolean [][]row = new boolean[9][9];
boolean [][]col = new boolean[9][9];
boolean [][]block = new boolean[9][9];
for (int i = 0; i < 9; i++) {
for (int j = 0; j < 9; j++) {
if(board[i][j]=='.')continue;
int num = board[i][j]-'1';//charToInt
if(row[num][i]||col[num][j]||block[num][i-i%3+j/3]){
return false;
}
//表示出现过
row[num][i]=col[num][j]=block[num][i-i%3+j/3]=true;
}
}
return true;
}
参考文章:http://blog.youkuaiyun.com/doc_sgl/article/details/13002461