package Order300;
import java.util.ArrayList; import java.util.List;
public class T37_sudoku_solver {
public static void main(String[] args) { new Solution() .solveSudoku( new char[][] { { '5', '3', '4', '6', '7', '8', '9', '1', '2' }, { '6', '7', '2', '1', '9', '5', '3', '4', '8' }, { '1', '9', '8', '3', '4', '2', '5', '6', '7' }, { '8', '5', '9', '7', '6', '1', '4', '2', '3' }, { '4', '2', '6', '8', '5', '3', '7', '9', '1' }, { '7', '1', '3', '9', '2', '4', '8', '5', '6' }, { '9', '6', '.', '.', '.', '.', '2', '8', '.' }, { '.', '.', '.', '4', '1', '9', '.', '.', '5' }, { '.', '.', '.', '.', '8', '.', '.', '7', '9' }, } ); }
static class Solution {
boolean[][] row = new boolean[9][9]; boolean[][] col = new boolean[9][9]; boolean[][][] cell = new boolean[3][3][9];
public void solveSudoku(char[][] board) { for (int xi = 0; xi < 9; xi++) { for (int yi = 0; yi < 9; yi++) { if (board[xi][yi] != '.') { int step = board[xi][yi] - '1'; row[xi][step] = true; col[yi][step] = true; cell[xi / 3][yi / 3][step] = true; } } } dfs(board, 0, 0); }
private boolean dfs(char[][] board, int x, int y) {
if (y == 9) { x++; y = 0; } if (x == 9) { return true; } if (board[x][y] != '.') {
return dfs(board, x, y + 1); }
for (int step = 0; step < 9; step++) { if (!(row[x][step] || col[y][step] || cell[x / 3][y / 3][step])) { board[x][y] = (char) (step + '1'); row[x][step] = col[y][step] = cell[x / 3][y / 3][step] = true; if (dfs(board, x, y + 1)) { return true; } board[x][y] = '.'; row[x][step] = col[y][step] = cell[x / 3][y / 3][step] = false; } } return false; } }
static class Solution_me_1 {
List<String> debugPrintBoard(char[][] board) { List<String> out = new ArrayList<>(); StringBuilder sb; for (int i = 0; i < 9; i++) { sb = new StringBuilder(); for (int j = 0; j < 9; j++) { sb.append(" "); sb.append(board[i][j]); } out.add(sb.toString()); } return out; }
List<Character> mixUp(boolean[] lineX, boolean[] lineY, boolean[] lineS) { int iMax = lineX.length; List<Character> out = new ArrayList<Character>(); for (int i = 0; i < iMax; i++) { if (!(lineX[i] || lineY[i] || lineS[i])) { out.add((char) (i + '1')); } } return out; }
boolean backtrack( char[][] board, boolean[][] lineX, boolean[][] lineY, boolean[][] lineS, int pi, int pj ) { searchNext:for (int i = pi; i < 9; i++) { for (int j = (i == pi ? pj : 0); j < 9; j++) { if (board[i][j] == '.') { pi = i; pj = j; break searchNext; } else if (i == 8 && j == 8) { return true; } } } List<Character> choices = mixUp( lineX[pi], lineY[pj], lineS[pi / 3 * 3 + pj / 3] ); for (char x : choices) { board[pi][pj] = x; lineX[pi][x - '1'] = true; lineY[pj][x - '1'] = true; lineS[pi / 3 * 3 + pj / 3][x - '1'] = true; if (backtrack(board, lineX, lineY, lineS, pi, pj)) { return true; } board[pi][pj] = '.'; lineX[pi][x - '1'] = false; lineY[pj][x - '1'] = false; lineS[pi / 3 * 3 + pj / 3][x - '1'] = false; } return false; }
public void solveSudoku(char[][] board) { boolean[][] lineX = new boolean[9][9]; boolean[][] lineY = new boolean[9][9]; boolean[][] lineS = new boolean[9][9];
for (int i = 0; i < 9; i++) { for (int j = 0; j < 9; j++) { if (board[i][j] != '.') { int val = board[i][j] - '1'; int sIndex = i / 3 * 3 + j / 3; lineX[i][val] = true; lineY[j][val] = true; lineS[sIndex][val] = true; } } }
backtrack(board, lineX, lineY, lineS, 0, 0); } } }
|