function spiral() {
$x = $y = $dx = $dy = 0;
$i = $l = 1;
while(++$l) {
// Get direction
[$dx, $dy] = match (true) {
$x > 0 && $y < 0 => [-1, 0], // Top right
$x < 0 && $y < 0 => [ 0, 1], // Top left
$x <= 0 && $y >= 0 => [ 1, 0], // Bottom left
$x > 0 && $y >= 0 => [ 0, -1], // Bottom right
};
$length = floor($l / 2); // Size of the current side
for ($j = 1; $j <= $length; $j++, $i++) {
yield [$x, $y, $i];
[$x, $y] = [$x + $dx, $y + $dy];
}
}
}
// ==================================================
// > PART 1
// ==================================================
foreach (spiral() as [$x, $y, $number]) if ($number == $input->int) break;
$solution_1 = abs($x) + abs($y);
// ==================================================
// > PART 2
// ==================================================
$grid = grid();
foreach (spiral() as [$x, $y, $number]) {
$value = $number == 1 ? 1 : $grid->getNeighbors([$x, $y], true)->filter()->sum();
$grid->set([$x, $y], $value);
if ($value > $input->int) break;
}
$solution_2 = $value;