#!/usr/bin/env tclsh set z 0; set zmin 0; set zmax 0 set w 0; set wmin 0; set wmax 0 set y -1; set ymin 1 set xmin 0 while {[gets stdin line] >= 0} { if {$line eq ""} continue incr y set x -1 foreach c [split $line {}] { incr x if {$c eq "#"} {set grid($x,$y,$z,$w) $c} } set xmax $x } set ymax $y proc neighbors {g x y z w} { upvar $g grid set x0 [expr {$x-1}]; set x1 [expr {$x+1}] set y0 [expr {$y-1}]; set y1 [expr {$y+1}] set z0 [expr {$z-1}]; set z1 [expr {$z+1}] set w0 [expr {$w-1}]; set w1 [expr {$w+1}] set n 0 for {set xx $x0} {$xx <= $x1} {incr xx} { for {set yy $y0} {$yy <= $y1} {incr yy} { for {set zz $z0} {$zz <= $z1} {incr zz} { for {set ww $w0} {$ww <= $w1} {incr ww} { if {$xx == $x && $yy == $y && $zz == $z && $ww == $w} continue if {[info exists grid($xx,$yy,$zz,$ww)]} { incr n } } } } } return $n } proc tick {} { global grid xmin xmax ymin ymax zmin zmax wmin wmax incr xmin -1; incr xmax incr ymin -1; incr ymax incr zmin -1; incr zmax incr wmin -1; incr wmax array set old [array get grid] array unset grid for {set x $xmin} {$x <= $xmax} {incr x} { for {set y $ymin} {$y <= $ymax} {incr y} { for {set z $zmin} {$z <= $zmax} {incr z} { for {set w $wmin} {$w <= $wmax} {incr w} { set n [neighbors old $x $y $z $w] if {! [info exists old($x,$y,$z,$w)]} { if {$n == 3} {set grid($x,$y,$z,$w) #} } else { if {$n == 2 || $n == 3} {set grid($x,$y,$z,$w) #} } } } } } } tick; tick; tick tick; tick; tick puts [array size grid]