Skip to content

Instantly share code, notes, and snippets.

@JamesEarle
Created November 20, 2013 17:06
Show Gist options
  • Save JamesEarle/7566894 to your computer and use it in GitHub Desktop.
Save JamesEarle/7566894 to your computer and use it in GitHub Desktop.
Recursive Sudoku Puzzle Solver
Medium
9 5 0 4 8 1 7 6 3
4 8 7 2 6 0 9 1 5
1 6 3 9 5 7 2 8 4
5 2 8 1 0 6 4 3 9
7 9 1 3 4 0 5 0 6
3 4 0 5 9 2 8 7 1
0 7 9 8 1 4 3 5 2
2 0 4 0 0 5 0 9 8
8 3 5 6 2 9 1 4 7
Easy
9 5 0 4 8 1 7 6 3
4 8 7 2 6 0 9 1 5
1 6 3 9 5 7 2 8 4
5 2 8 1 7 6 4 3 9
7 9 1 3 4 8 5 0 6
3 4 6 5 9 2 8 7 1
6 7 9 8 1 4 3 5 2
2 0 4 7 0 5 6 9 8
8 3 5 6 2 9 1 4 7
Valid
2 5 4 7 8 9 3 6 1
8 1 3 4 2 6 9 5 7
6 7 9 5 3 1 2 8 4
5 6 8 3 1 7 4 2 9
7 4 2 8 9 5 1 3 6
9 3 1 2 6 4 5 7 8
3 2 6 1 4 8 7 9 5
1 8 7 9 5 2 6 4 3
4 9 5 6 7 3 8 1 2
Invalid
1 2 3 4 5 6 7 8 9
2 3 4 5 6 7 8 9 1
3 4 5 6 7 8 9 1 2
4 5 6 7 8 9 1 2 3
5 6 7 8 9 1 2 3 4
6 7 8 9 1 2 3 4 5
7 8 9 1 2 3 4 5 6
8 9 1 2 3 4 5 6 7
9 1 2 3 4 5 6 7 8
package PartB;
/*
* Reads Sudoku Puzzle as ASCIIDataFile, will brute
* force combinations until the SolutionValidator
* returns true.
*
* @author James Earle
*/
import BasicIO.*;
public class PuzzleSolver {
ASCIIDataFile puzzle;
ASCIIDisplayer d;
int [] [] p;
int [] a;
public PuzzleSolver ( ) {
puzzle = new ASCIIDataFile();
d = new ASCIIDisplayer();
p = new int [9][9];
int z;
int count = 0;
for (int j = 0; j<9; j++) {
for (int i = 0; i<9; i++) {
z = puzzle.readInt();
p[j][i] = z;
if (z == 0) {
count++;
}
}
}
a = new int [count];
for (int k = 0; k<count; k++) {
a[k] = 1;
}
generate(a.length-1);
}
public boolean generate (int i) { //i is the index length -1
if (i == a.length) {
return valid(p);
} else {
valid(p);
generate(i+1);
}
boolean solution = true;
int value = 1;
int end = a.length;
d.writeInt(i);
d.writeInt(value);
a[i] = value;
generate(i+1);
if (i+1 == end) {
value = 2;
generate(i);
}
i++;
return solution;
} //generate
public boolean valid (int [] [] p) {
int val;
boolean valid = true;
for (int j = 0; j<9; j++) { //Columns counter
for (int i = 0; i<9; i++) { //Row counter
val = p[j][i];
for (int k = 0; k<9; k++) { //Checks every
if (val == p[k][i] && k != j) {
printSolution(p,false);
return false;
}
}
for (int l = 0; l<9; l++) { //Row checker
if (val == p[j][l] && l != i) {
printSolution(p,false);
return false;
}
}
}
}
/* Using x and z as counters as well as pointers towards the
* index locations, we use the checkSquare method to validate
* every square in the Sudoku puzzle. There are 9 squares,
* whose top-left index location's are:
* (0,0),(0,3),(0,6)
* (3,0),(3,3),(3,6)
* (6,0),(6,3),(6,6)
*/
int x = 0;
int z = 0;
boolean [] oneToNine = new boolean [9];
while (x <= 6) {
if (checkSquare(x,z,p,oneToNine) == false) {
printSolution(p,false);
return false;
}
if (z==6) {
x = x+3;
z = 0;
}
z = z+3;
}
printSolution(p,valid);
return valid;
} //Valid
private boolean checkSquare (int a, int b, int [] [] p, boolean [] oneToNine) {
int aCondition = a + 3;
int bCondition = b + 3;
boolean checked = true;
for (int k = 9; k>0; k--) {
for (int j = a; j<aCondition; j++) {
for (int i = b; i<bCondition; i++) {
if (p[j][i] == k) {
oneToNine[k-1] = true;
}
}
}
}
for (int x = 0; x<oneToNine.length; x++) {
if (oneToNine[x] == false) {
return false;
}
}
return checked;
} //checkSquare
private void printSolution (int [] [] p, boolean valid) {
int a;
for (int j = 0; j<9; j++) {
for (int i = 0; i<9; i++) {
d.writeString("| "+p[j][i]);
if (i == 8) {
d.writeString(" |");
d.newLine();
}
}
}
if (valid == true) {
d.writeString(" The puzzle solution is valid.");
} else {
d.writeString(" The puzzle solution is invalid.");
}
} //printSolution
public static void main ( String[] args ) { new PuzzleSolver(); };
}
package PartA;
/*
* Solutions generated recursively are tested for validity here.
* If the solution fills a puzzle, and every column, row, and 3x3 square
* contain 1-9 with no overlap, it returns true.
*
* @author James Earle
*/
import BasicIO.*;
public class SolutionValidator {
ASCIIDataFile file;
ASCIIDisplayer d;
public SolutionValidator ( ) {
file = new ASCIIDataFile();
d = new ASCIIDisplayer();
int [] [] a = new int [9] [9];
for (int j = 0; j<9; j++) {
for (int i = 0; i<9; i++) {
a[j][i] = file.readInt();
}
}
valid (a);
}
public boolean valid (int [] [] p) {
int val;
boolean valid = true;
for (int j = 0; j<9; j++) { //Columns counter
for (int i = 0; i<9; i++) { //Row counter
val = p[j][i];
for (int k = 0; k<9; k++) { //Checks every
if (val == p[k][i] && k != j) {
printSolution(p,false);
return false;
}
}
for (int l = 0; l<9; l++) { //Row checker
if (val == p[j][l] && l != i) {
printSolution(p,false);
return false;
}
}
}
}
/* Using x and z as counters as well as pointers towards the
* index locations, we use the checkSquare method to validate
* every square in the Sudoku puzzle. There are 9 squares,
* whose top-left index location's are:
* (0,0),(0,3),(0,6)
* (3,0),(3,3),(3,6)
* (6,0),(6,3),(6,6)
*/
int x = 0;
int z = 0;
boolean [] oneToNine = new boolean [9];
while (x <= 6) {
if (checkSquare(x,z,p,oneToNine) == false) {
printSolution(p,false);
return false;
}
if (z==6) {
x = x+3; //Increments every round.
z = 0;
}
z = z+3; //Increments every three rounds.
}
printSolution(p,valid);
return valid;
} //Valid
private boolean checkSquare (int a, int b, int [] [] p, boolean [] oneToNine) {
int aCondition = a + 3;
int bCondition = b + 3;
boolean checked = true;
for (int k = 9; k>0; k--) {
for (int j = a; j<aCondition; j++) {
for (int i = b; i<bCondition; i++) {
if (p[j][i] == k) {
oneToNine[k-1] = true;
}
}
}
}
for (int x = 0; x<oneToNine.length; x++) {
if (oneToNine[x] == false) {
return false;
}
}
return checked;
} //checkSquare
private void printSolution (int [] [] p, boolean valid) {
int a;
for (int j = 0; j<9; j++) {
for (int i = 0; i<9; i++) {
d.writeString("| "+p[j][i]);
if (i == 8) {
d.writeString(" |");
d.newLine();
}
}
}
if (valid == true) {
d.writeString(" The puzzle solution is valid.");
} else {
d.writeString(" The puzzle solution is invalid.");
}
} //printSolution
public static void main ( String[] args ) { new SolutionValidator(); };
} //SolutionValidator
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment