题目:
Write a program to solve a Sudoku puzzle by filling the empty cells.
Empty cells are indicated by the character '.'
.
You may assume that there will be only one unique solution.
A sudoku puzzle...
...and its solution numbers marked in red. (Hard)
分析:
DFS搜索,但是不太好写。依次尝试所有可能的数字,然后递归地继续向后添加,发现当填入任何数字都无法满足条件(行列九宫格)后返回false(说明前面填错了)。
想清楚递归地过程的话也不是很难理解。
注意事项:
1.每个数字添加后判断本行,本列和所在九宫格即可,不必判断所有数独内容;
2.自己依照上一题isValid函数写的条件判定代码。导致少了一个board[i][j] != '.'的判断(见代码注释部分),导致所有情况都返回false(因为其会对flag['.' - '0']赋值为1,然后判断等于1)这里错了好久才发现。
代码:
1 class Solution { 2 private: 3 bool isValid (vector<vector<char>>& board, int x, int y) { 4 int flag[10] = {0}; 5 for (int i = 0; i < board.size(); ++i) { 6 if (board[x][i] != '.') { //少了这句会导致这个判断总是false!!! 7 if (flag[board[x][i] - '0'] == 1) { 8 return false; 9 } 10 else { 11 flag[board[x][i] - '0'] = 1; 12 } 13 } 14 } 15 memset(flag,0,sizeof(flag)); 16 for (int i = 0; i < board.size(); ++i) { 17 if (board[i][y] != '.') { 18 if (flag[board[i][y] - '0'] == 1) { 19 return false; 20 } 21 else { 22 flag[board[i][y] - '0'] = 1; 23 } 24 } 25 } 26 memset(flag,0,sizeof(flag)); 27 int sqx = (x / 3) * 3; 28 int sqy = (y / 3) * 3; 29 for (int i = sqx; i < sqx + 3; ++i) { 30 for (int j = sqy; j < sqy + 3; ++j) { 31 if (board[i][j] != '.') { 32 if (flag[board[i][j] - '0'] == 1) { 33 return false; 34 } 35 else { 36 flag[board[i][j] - '0'] = 1; 37 } 38 } 39 } 40 } 41 return true; 42 } 43 bool solvehelper(vector<vector<char>>& board) { 44 for (int i = 0; i < board.size(); ++i) { 45 for (int j = 0; j < board.size(); ++j) { 46 if (board[i][j] == '.') { 47 for (int k = 0; k < 9; ++k) { 48 board[i][j] = '1' + k; 49 if (isValid(board, i, j)) { 50 if (solvehelper(board)) { 51 return true; 52 } 53 } 54 } 55 board[i][j] = '.'; 56 return false; 57 } 58 } 59 } 60 return true; 61 } 62 public: 63 void solveSudoku(vector<vector<char>>& board) { 64 bool b = solvehelper(board); 65 } 66 };