private void OmissionDelete(int number, string scope, List <Field> ignore, Sudoku sudoku) { int index = sudoku.IndexOf(ignore[0]); List <Field> candidates = new List <Field>(); if (scope == "row" || scope == "column") { candidates = Solver.GetEmptyFieldsInSquare(index, sudoku); } else if (scope == "square") { if (Solver.AreSameRow(ignore[0], ignore[1], sudoku)) { candidates = Solver.GetEmptyFieldsInRow(index, sudoku); } else { candidates = Solver.GetEmptyFieldsInColumn(index, sudoku); } } foreach (Field field in ignore) { candidates.Remove(field); } foreach (Field candidate in candidates) { int toRemoveIndex = sudoku.IndexOf(candidate); Solver.locker.WaitingAcquire(toRemoveIndex); candidate.RemovePossibility(number); Solver.locker.Release(toRemoveIndex); } }
public static bool AreSameColumn(Field field1, Field field2, Sudoku sudoku) { int index1 = sudoku.IndexOf(field1); int index2 = sudoku.IndexOf(field2); index1 = index1 % 9; index2 = index2 % 9; if (index1 == index2) { return(true); } return(false); }
public static bool AreSameSquare(Field field1, Field field2, Sudoku sudoku) { int index1 = sudoku.IndexOf(field1); int index2 = sudoku.IndexOf(field2); index1 = (index1 / 27 * 27) + (index1 % 9) - (index1 % 3); index2 = (index2 / 27 * 27) + (index2 % 9) - (index2 % 3); if (index1 == index2) { return(true); } return(false); }
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); } }
private void OmissionSearch(List <Field> candidates, string scope, Sudoku sudoku) { int[] numberList = new int[0]; if (scope == "row") { numberList = Solver.GetMissingNumbersInRow(sudoku.IndexOf(candidates[0]), sudoku); } else if (scope == "column") { numberList = Solver.GetMissingNumbersInColumn(sudoku.IndexOf(candidates[0]), sudoku); } else if (scope == "square") { numberList = Solver.GetMissingNumbersInColumn(sudoku.IndexOf(candidates[0]), sudoku); } foreach (int i in numberList) { List <Field> foundAppearances = new List <Field>(); bool skipNumber = false; for (int t = 0; t < candidates.Count; t++) { Field field = candidates[t]; if (field.GetPossibilities().Contains(i)) { for (int k = t + 1; k < candidates.Count; k++) { if (candidates[k].GetPossibilities().Contains(i)) { if (scope == "row" || scope == "column") { if (!Solver.AreSameSquare(field, candidates[k], sudoku)) { skipNumber = true; break; } } else if (scope == "square") { if (!Solver.AreSameRow(field, candidates[k], sudoku) && !Solver.AreSameColumn(field, candidates[k], sudoku)) { skipNumber = true; break; } } if (!foundAppearances.Contains(field)) { foundAppearances.Add(field); } if (!foundAppearances.Contains(candidates[k])) { foundAppearances.Add(candidates[k]); } } } if (skipNumber) { break; } } } if (!skipNumber && foundAppearances.Count > 1) { OmissionDelete(i, scope, foundAppearances, sudoku); } } }
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)); } }