LazySolver::solve()   A
last analyzed

Complexity

Conditions 4
Paths 5

Size

Total Lines 18
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 4
eloc 9
c 1
b 0
f 0
nc 5
nop 1
dl 0
loc 18
rs 9.9666
1
<?php declare(strict_types=1);
2
3
namespace Stratadox\PuzzleSolver\Solver;
4
5
use Stratadox\PuzzleSolver\Puzzle;
6
use Stratadox\PuzzleSolver\PuzzleSolver;
7
use Stratadox\PuzzleSolver\PuzzleSolution;
8
use Stratadox\PuzzleSolver\SearchStrategy\SearchStrategyFactory;
9
use Stratadox\PuzzleSolver\Solutions;
10
11
/**
12
 * Lazy puzzle solvers will continue to look for solutions until they've found
13
 * *all* valid solutions. Lazy solvers can be used for puzzles that require more
14
 * than one solution.
15
 *
16
 * @author Stratadox
17
 */
18
final class LazySolver implements PuzzleSolver
19
{
20
    /** @var SearchStrategyFactory */
21
    private $strategy;
22
23
    private function __construct(SearchStrategyFactory $strategy)
24
    {
25
        $this->strategy = $strategy;
26
    }
27
28
    public static function using(SearchStrategyFactory $strategy): PuzzleSolver
29
    {
30
        return new self($strategy);
31
    }
32
33
    public function solve(Puzzle $puzzle): Solutions
34
    {
35
        $search = $this->strategy->begin($puzzle);
36
        $solutions = [];
37
38
        while ($search->isOngoing()) {
39
            $puzzleState = $search->nextCandidate();
40
41
            if ($puzzleState->isSolved()) {
42
                $solutions[] = PuzzleSolution::fromSolved($puzzleState, $puzzle);
43
            }
44
45
            foreach ($puzzleState->possibleMoves() as $move) {
46
                $search->consider($puzzleState->afterMaking($move));
47
            }
48
        }
49
50
        return new Solutions(...$solutions);
51
    }
52
}
53