Skip to content

Instantly share code, notes, and snippets.

@DataKinds
Last active August 29, 2015 14:07
Show Gist options
  • Save DataKinds/65e247be4b093fb15f78 to your computer and use it in GitHub Desktop.
Save DataKinds/65e247be4b093fb15f78 to your computer and use it in GitHub Desktop.
Fun little game of life implementation, based on https://www.youtube.com/watch?v=a9xAKttWgP4
import Control.Applicative
import Control.Concurrent
import System.Console.ANSI
import Data.List.Split
import Data.Char
mainGridString :: IO String
mainGridString = readFile "grid"
parseGrid :: String -> Grid
parseGrid grid = (map . map) digitToInt (lines grid)
type CellInfo = (Int, Int) --Cell alive status, cell population
type Grid = [[Int]]
type GridWithCellInfo = [[CellInfo]]
shiftUp :: Grid -> Grid
shiftUp grid = tail grid ++ [head grid]
shiftDown :: Grid -> Grid
shiftDown grid = last grid : init grid
shiftLeft :: Grid -> Grid
shiftLeft grid = zipWith (++) (verticalTail) (verticalHead)
where verticalHead = map (:[]) (map (head) grid)
verticalTail = map (tail) grid
shiftRight :: Grid -> Grid
shiftRight grid = zipWith (++) (verticalLast) (verticalInit)
where verticalInit = map (init) grid
verticalLast = map (:[]) (map (last) grid)
shiftedGrids :: Grid -> [Grid]
shiftedGrids grid = [shiftUp grid, shiftDown grid, shiftLeft grid, shiftRight grid, (shiftDown . shiftRight) grid, (shiftDown . shiftLeft) grid, (shiftUp . shiftRight) grid, (shiftUp . shiftLeft) grid]
populationMap :: Grid -> GridWithCellInfo
populationMap grid = gridToTuple (grid) (foldr1 (addGrids) (shiftedGrids grid))
where addGrids = (zipWith . zipWith) (+) :: Grid -> Grid -> Grid
gridToTuple = (zipWith . zipWith) (\alive population -> (alive, population)) :: Grid -> Grid -> GridWithCellInfo
isDedOrNot :: CellInfo -> Int --Takes CellInfo, Outputs whether or not the cell is alive
isDedOrNot cellInfo
| population < 2 = 0
| population == 2 && alive == 1 = 1
| population == 2 && alive == 0 = 0
| population == 3 = 1
| population > 3 = 0
where population = snd cellInfo
alive = fst cellInfo
lifeIteration :: Grid -> Grid
lifeIteration grid = (map . map) (isDedOrNot) (populationMap grid)
animation :: Grid -> IO Grid
animation grid = do mapM_ putStrLn $ replicate 500 ""
mapM_ putStrLn (map concat ((map . map) numberToString grid))
threadDelay 500000 -- 0.5 second.. in microseconds :/
animation (lifeIteration grid)
where numberToString 0 = "."
numberToString 1 = "X"
main :: IO ()
--main = do
-- mapM_ putStrLn (map show (populationMap mainGrid))
-- putStrLn ""
-- mapM_ putStrLn (map show mainGrid)
-- putStrLn ""
-- mapM_ putStrLn (map show (lifeIteration mainGrid))
-- putStrLn ""
-- mapM_ putStrLn (map show (lifeIteration $ lifeIteration mainGrid))
main = do
grid <- mainGridString
animation (parseGrid grid)
putStrLn ""
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment