$grid = (array) $input->lines->map("str_split");
[$w, $h] = [count($grid[0]), count($grid)];
$s = $input->replace("\n", "")->search("S");
[$xs, $ys] = [$s % $w, intdiv($s, $w)];
$max = ($xs + 2 * $w) + 1;
$graph = new Graph(function ($graph) use ($grid, $max, $w, $h) {
[$x, $y, $steps] = explode(";", $graph->current);
$graph->steps[$steps % 2 ? "odd" : "even"]["$x;$y"] = true;
if (($graph->exploring??null) != $steps) {
$graph->exploring = $steps;
if ($steps != $max) {
$prev = $steps + 1;
$graph->counts[($max - $prev)] = count($graph->steps[$prev % 2 ? "odd" : "even"]??[]);
}
}
if (--$steps < 0) return [];
$next = [];
foreach (neighbors([$x, $y]) as $n) {
if ($grid[Math::mod($n[1], $h)][Math::mod($n[0], $w)] == "#") continue;
$n = implode(";", $n);
if (isset($graph->steps["even"][$n]) || isset($graph->steps["odd"][$n])) continue;
$next[$n . ";$steps"] = 1;
}
return $next;
});
$graph->explore("$xs;$ys;$max");
// ==================================================
// > PART 1
// ==================================================
$solution_1 = $graph->counts[64];
// ==================================================
// > PART 2 : Quadratic polynomial
// ==================================================
[$f0, $f1, $f2] = [$graph->counts[$xs], $graph->counts[$xs + $w], $graph->counts[$xs + 2 * $w]];
$a = ($f2 - 2*$f1 + $f0) / 2;
$b = $f1 - $f0 - $a;
$c = $f0;
$f = fn ($n) => $a*$n**2 + $b*$n + $c;
$n = (26501365 - $xs) / $w;
$solution_2 = $f($n);