static void solveLogic(PuzzleState puzzleState) { bool makeLinks = true; int iterations = 0; while (makeLinks) { makeLinks = false; List <Point> nodes = puzzleState.Nodes.Keys.ToList(); foreach (Point n in nodes) { //Skip a saturated node int remaining = puzzleState.Nodes[n]; if (remaining == 0) { continue; } //Calculate links int requiredLinks = remaining; int availableLinks = puzzleState.GetNodeLinksAvailable(n); if (requiredLinks == availableLinks) { //Populate links if required links equals available links //Console.Error.WriteLine("LinkAll n=(" + n.X + "," + n.Y + ") links=" + requiredLinks); makeLinks = true; puzzleState.LinkNeighbours(n); puzzleState.LinkNeighbours(n); continue; } //Calculate requirements int requiredDegrees = PuzzleState.GetNodeDegreesRequired(remaining); int availableDegrees = puzzleState.GetNodeDegreesAvailable(n); if (requiredDegrees == availableDegrees) { //Populate links if the available degrees of freedom equals required //Console.Error.WriteLine("LinkNeighbours n=(" + n.X + "," + n.Y + ") links=" + requiredLinks + "," + availableLinks + " degrees=" + requiredDegrees); makeLinks = true; puzzleState.LinkNeighbours(n); } else if (availableDegrees - requiredDegrees == 1) { //Special case for 2->1, 4->1, 6->1 if (puzzleState.Nodes[n] % 2 == 0) { foreach (Point neighbour in Neighbours[n]) { if (puzzleState.CanLink(n, neighbour) == 1) { //Console.Error.WriteLine("LinkNeighbours -1 n=(" + n.X + "," + n.Y + ") links=" + requiredLinks + "," + availableLinks + " degrees=" + requiredDegrees); //Link others except neighbour foreach (Point candidate in Neighbours[n]) { if (!candidate.Equals(neighbour) && (puzzleState.CanLink(n, candidate) > 0)) { makeLinks = true; puzzleState.AddLink(n, candidate); } } //One iteration break; } } } } } iterations++; //Console.Error.WriteLine(new string(' ', level) + " Finished " + iterations + " iterations"); } }