数独破解(回溯,暴力dfs+剪枝)
2017-04-22 00:04
435 查看
问题描述:对于一个给定的9*9方格里,填了若干数字,且满足以下条件:
① 每个横行和竖列中的9个格子都包含数字1~9,且不重复;
② 每个黑色粗实线围住的9个格子(3×3)都包含数字1~9,且不重复
思路:从左上角开始,通过对每一个没有填数的格子进行1到9的遍历,然后通过约束函数来判断该该格子的填数是否符合规则,若符合就递进到下一个(即右边的格子),假若下一个格子已超出右边界,则递进到下一行的第0个格子处,依此类推,直到超出下边界,即完成其中一种数独填数!
① 每个横行和竖列中的9个格子都包含数字1~9,且不重复;
② 每个黑色粗实线围住的9个格子(3×3)都包含数字1~9,且不重复
思路:从左上角开始,通过对每一个没有填数的格子进行1到9的遍历,然后通过约束函数来判断该该格子的填数是否符合规则,若符合就递进到下一个(即右边的格子),假若下一个格子已超出右边界,则递进到下一行的第0个格子处,依此类推,直到超出下边界,即完成其中一种数独填数!
import java.util.Scanner; public class Main { static int count = 0;// 记录该数独的解法个数 public static void main(String[] args) { Scanner in = new Scanner(System.in); int[][] map = new int[9][9]; for (int i = 0; i < 9; i++) for (int j = 0; j < 9; j++) map[i][j] = in.nextInt(); f(map, 0, 0); } public static void f(int[][] map, int x, int y) { if (x > 8) { System.out.println("第" + ++count + "种解法:"); for (int i = 0; i < 9; i++) { for (int j = 0; j < 9; j++) System.out.print(map[i][j] + " "); System.out.println(); } return; } if (y > 8) { f(map, x + 1, 0); return; } // 0表示没有填数 if (map[x][y] == 0) { for (int k = 1; k <= 9; k++) { map[x][y] = k; if (OK(map, x, y)) f(map, x, y + 1); } map[x][y] = 0; } else f(map, x, y + 1); } private static boolean OK(int[][] map, int x, int y) { // 判断列 for (int i = 0; i < 9; i++) if (map[i][y] == map[x][y] && i != x) return false; // 判断行 for (int i = 0; i < 9; i++) if (map[x][i] == map[x][y] && i != y) return false; // 判断九宫格,找到当前判断格子 所属的九宫格 int leftx = x / 3 * 3;// lextx为目前所在的九宫格的起始x坐标,即九宫格左上角的x坐标 int lefty = y / 3 * 3;// lexty为目前所在的九宫格的起始y坐标 int endx = leftx + 2;// endx为目前所在的九宫格的末尾x坐标,即九宫格右下角的x坐标 int endy = lefty + 2;// endx为目前所在的九宫格的末尾x坐标,即九宫格右下角的y坐标 for (int i = leftx; i <= endx; i++) for (int j = lefty; j <= endy; j++) { if (i == x && j == y) continue; if (map[i][j] == map[x][y]) return false; } // 通过检测 return true; } } /* Input: 0 6 1 0 3 0 0 2 0 0 5 0 0 0 8 1 0 7 0 0 0 0 0 7 0 3 4 0 0 9 0 0 6 0 7 8 0 0 3 2 0 9 5 0 0 5 7 0 3 0 0 9 0 0 1 9 0 7 0 0 0 0 0 8 0 2 4 0 0 0 6 0 0 0 0 0 0 0 0 0 0 Output: 第1种解法: 7 6 1 9 3 4 8 2 5 3 5 4 6 2 8 1 9 7 9 2 8 1 5 7 6 3 4 2 1 9 5 4 6 3 7 8 4 8 3 2 7 9 5 1 6 5 7 6 3 8 1 9 4 2 1 9 5 7 6 2 4 8 3 8 3 2 4 1 5 7 6 9 6 4 7 8 9 3 2 5 1 第2种解法: 7 6 1 9 3 4 8 2 5 3 5 4 6 2 8 1 9 7 9 2 8 1 5 7 6 3 4 2 1 9 5 4 6 3 7 8 4 8 3 2 7 9 5 1 6 5 7 6 3 8 1 9 4 2 1 9 5 7 6 2 4 8 3 8 3 2 4 9 5 7 6 1 6 4 7 8 1 3 2 5 9 */ }
相关文章推荐
- LeetCode-90-Subsets II 暴力dfs回溯
- Sudoku Solver 破解数独 @LeetCode 附DFS感想
- HDU-5937 Equation(暴力DFS+剪枝)
- POJ 2676 Sudoku (DFS回溯剪枝)
- hdu4499 超暴力dfs回溯
- HDU 4431 Mahjong (DFS,暴力枚举,剪枝)
- POJ 2531 dfs回溯(小剪枝)
- hdu 5547 Sudoku dfs 暴力回溯 解题报告
- poj The Settlers of Catan( 求图中的最长路 小数据量 暴力dfs搜索(递归回溯))
- HDU-1015 Safecracker(DFS+暴力回溯 / 五重循环)
- 蓝桥杯 基础练习 2n皇后问题 (简单dfs暴力+优化剪枝)
- POJ - 3900 The Robbery (DFS+暴力剪枝)
- Uva140 Bandwidth 【dfs回溯+剪枝】【例题7-6】
- hdu1010 Tempter of the Bone(DFS,剪枝,递归,回溯)
- 数独问题(DFS回溯)
- HDU 1010 Tempter of the Bone(DFS回溯+剪枝)
- HDOJ 5547 Sudoku (DFS 数独填数+回溯)
- hdu 3325 Arithmetically Challenged(dfs全排+暴力枚举破解+set集合的应用)
- 八皇后问题 DFS,回溯剪枝 //http://poj.grids.cn/practice/2698
- POJ1416 Shredding Company ACM解题报告(DFS回溯+剪枝)