/// <summary> /// If the number is the only possibility in a row/column/square /// even if there are more possibilities for this field, /// then this number will be set. /// </summary> public void Solve(object param) { Sudoku sudoku = (Sudoku)param; int index = 0; do { if (Solver.locker.Acquire(index)) { if (sudoku.GetField(index).Value == 0) { int horizontal = index / 9 * 9; int vertical = index % 9; int square = (index / 27 * 27) + (index % 9) - (index % 3); List <int> ownPossibilities = sudoku.GetPossibilities(index); // Get all fields in a row/column/square foreach (int value in ownPossibilities) { Field field; bool foundHorizontal = false; bool foundVertical = false; bool foundSquare = false; for (int i = 0; i < 9; i++) { field = sudoku.GetField(horizontal + i); if ((horizontal + i) != index && (field.Value == value || field.GetPossibilities().Contains(value))) { foundHorizontal = true; break; } } for (int i = 0; i < (73 + vertical); i += 9) { field = sudoku.GetField(vertical + i); if ((vertical + i) != index && (field.Value == value || field.GetPossibilities().Contains(value))) { foundVertical = true; break; } } for (int j = 0; j <= 18; j += 9) { for (int i = 0; i < 3; i++) { field = sudoku.GetField(square + i + j); if ((square + i + j) != index && (field.Value == value || field.GetPossibilities().Contains(value))) { foundSquare = true; break; } } } if (!foundHorizontal || !foundVertical || !foundSquare) { sudoku.Set(index, value); sudoku.RemoveAllPossibilities(index); } } } Solver.locker.Release(index); } index = (index + 1) % Sudoku.SIZE; } while (!Solver.IsSolved()); }
private void NakedGroupSearch(List <Field> candidates, Sudoku sudoku) { for (int k = 0; k < candidates.Count; k++) { Field field = candidates[k]; List <Field> pair = new List <Field>(); List <Field> triple = new List <Field>(); List <Field> quad = new List <Field>(); List <int> ownPossibilities = field.GetPossibilities(); Solver.locker.WaitingAcquire(sudoku.IndexOf(field)); for (int j = k + 1; j < candidates.Count; j++) { if (field.HasIdenticalPossibilities(candidates[j])) { // Look for pairs if (ownPossibilities.Count == 2) { pair.Add(candidates[j]); } // Look for triples else if (ownPossibilities.Count == 3) { triple.Add(candidates[j]); } // Look for quads else if (ownPossibilities.Count == 4) { quad.Add(candidates[j]); } } } // The pair is full with one, because the first one is "field" which is not in the list if (pair.Count == 1) { pair.Add(field); candidates.Remove(pair[0]); candidates.Remove(pair[1]); NakedGroupRemove(candidates, field.GetPossibilities(), sudoku); } // The triple is full with two, because the first one is "field" which is not in the list if (triple.Count == 2) { triple.Add(field); candidates.Remove(triple[0]); candidates.Remove(triple[1]); candidates.Remove(triple[2]); NakedGroupRemove(candidates, field.GetPossibilities(), sudoku); } // The quad is full with three, because the first one is "field" which is not in the list if (quad.Count == 3) { quad.Add(field); candidates.Remove(quad[0]); candidates.Remove(quad[1]); candidates.Remove(quad[2]); candidates.Remove(quad[3]); NakedGroupRemove(candidates, field.GetPossibilities(), sudoku); } Solver.locker.Release(sudoku.IndexOf(field)); } }
private void NakedGroupRemove(List <Field> candidates, List <int> possibilities, Sudoku sudoku) { foreach (Field otherField in candidates) { int index = sudoku.IndexOf(otherField); Solver.locker.WaitingAcquire(index); for (int i = 0; i < possibilities.Count; i++) { sudoku.GetField(index).RemovePossibility(possibilities[i]); } Solver.locker.Release(index); } }
public Solver(Sudoku sudoku) { Solver.sudoku = sudoku; }
public void PassUserEntry(int[][] gridToSolve) { sudoku = new Sudoku(gridToSolve); }
public Controller() { sudoku = new Sudoku(); }