Initial (and probably only) commit

This commit is contained in:
Joop Schilder 2019-12-22 00:00:47 +01:00
commit 3082c28458

84
game_of_life.php Normal file
View File

@ -0,0 +1,84 @@
<?php
/*
* Game of Life in PHP using pure functions
*
* Joop Schilder
*/
if (version_compare(PHP_VERSION, '7.0') < 1) {
throw new RuntimeException('PHP>=7.0 required');
}
const BOARDSIZE = 32;
CONST DELAY_MS = 200;
const DEAD = 0;
const ALIVE = 1;
function get_neighbours(array $board, int $i, int $j): array
{
$neighbours = [];
for ($ni = $i - 1; $ni <= $i + 1; $ni++) {
for ($nj = $j - 1; $nj <= $j + 1; $nj++) {
if (isset($board[$ni][$nj]) && ($ni !== $i || $nj !== $j)) {
$neighbours[] = $board[$ni][$nj];
}
}
}
return $neighbours;
}
function get_next_cell_state(array $board, int $i, int $j): int
{
$living_neighbours = count(array_filter(get_neighbours($board, $i, $j), function (int $state): bool {
return $state === ALIVE;
}));
$is_alive = $board[$i][$j] === ALIVE ? ($living_neighbours > 1 && $living_neighbours < 4) : $living_neighbours === 3;
return $is_alive ? ALIVE : DEAD;
}
function get_next_board_state(array $board): array
{
$next_board = [];
for ($i = 0; $i < BOARDSIZE; $i++) {
for ($j = 0; $j < BOARDSIZE; $j++) {
$next_board[$i][$j] = get_next_cell_state($board, $i, $j);
}
}
return $next_board;
}
function print_board(array $board): void
{
system('WIN' === strtoupper(substr(PHP_OS, 0, 3)) ? 'cls' : 'clear');
print('┌' . str_repeat('─', 2 * BOARDSIZE) . '┐' . PHP_EOL);
for ($i = 0; $i < BOARDSIZE; $i++) {
print('│');
for ($j = 0; $j < BOARDSIZE; $j++) {
print($board[$i][$j] === ALIVE ? '██' : '░░');
}
print('│' . PHP_EOL);
}
print('└' . str_repeat('─', 2 * BOARDSIZE) . '┘' . PHP_EOL);
}
$board = [];
for ($i = 0; $i < BOARDSIZE; $i++) {
for ($j = 0; $j < BOARDSIZE; $j++) {
$board[$i][$j] = DEAD;
}
}
// Glider
$board[1][3] = ALIVE;
$board[2][4] = ALIVE;
$board[3][2] = ALIVE;
$board[3][3] = ALIVE;
$board[3][4] = ALIVE;
while (true) {
print_board($board);
usleep(DELAY_MS * 1000);
$board = get_next_board_state($board);
}