private void UpdateCanOpenOrFlag(SolveCellType[] candidate, bool[] canOpen, bool[] canFlag) { var min = candidate.Count(c => c == SolveCellType.Mine); var max = candidate.Count(c => c == SolveCellType.Mine || c == SolveCellType.Uncertain || c == SolveCellType.Undef); if (min > MineCount || max < MineCount) return; var betterCandidate = candidate; if (min == MineCount) betterCandidate = candidate.Select(c => (c == SolveCellType.Uncertain || c == SolveCellType.Undef) ? SolveCellType.Empty : c).ToArray(); if (max == MineCount) betterCandidate = candidate.Select(c => (c == SolveCellType.Uncertain || c == SolveCellType.Undef) ? SolveCellType.Mine : c).ToArray(); betterCandidate.ForEach((t, i) => { if (t != SolveCellType.Empty) canOpen[i] = false; if (t != SolveCellType.Mine) canFlag[i] = false; }); }
private void SolveRec(int index, SolveCellType[] candidate, bool[] canOpen, bool[] canFlag) { if (index == Cells.Length) { UpdateCanOpenOrFlag(candidate, canOpen, canFlag); return; } if (candidate[index] != SolveCellType.Undef) { SolveRec(index + 1, candidate, canOpen, canFlag); return; } //可能性のある解 var mine = true; var empty = true; foreach (var n in Neighbors(index)) { if(!Cells[n].Open) continue; var ms = Neighbors(n); if (ms.Count(i => candidate[i] == SolveCellType.Mine) >= Cells[n].SafeNeighborMineCount) mine = false; if (ms.Count(i => candidate[i] == SolveCellType.Empty) >= ms.Count - Cells[n].SafeNeighborMineCount) empty = false; if (!(mine || empty)) return; } if(mine) { candidate[index] = SolveCellType.Mine; SolveRec(index + 1, candidate, canOpen, canFlag); } if (empty) { candidate[index] = SolveCellType.Empty; SolveRec(index + 1, candidate, canOpen, canFlag); } candidate[index] = SolveCellType.Undef; return; }