day10
This commit is contained in:
		
							
								
								
									
										64
									
								
								day10/main.hs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										64
									
								
								day10/main.hs
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,64 @@
 | 
			
		||||
import System.IO
 | 
			
		||||
 | 
			
		||||
import Data.List.Split
 | 
			
		||||
 | 
			
		||||
import Debug.Trace
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
data Cycle = Noop | Addx1 | Addx2 Int deriving (Show)
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
parseInstr :: String -> [Cycle]
 | 
			
		||||
parseInstr ('n':_) = [Noop]
 | 
			
		||||
parseInstr ('a':xs) = [Addx1,Addx2 dx]
 | 
			
		||||
    where
 | 
			
		||||
        dxs = last $ splitOn " " xs
 | 
			
		||||
        dx  = read dxs :: Int
 | 
			
		||||
 | 
			
		||||
parseAsm :: String -> [Cycle]
 | 
			
		||||
parseAsm = concat . map parseInstr . lines
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
computeX :: Int -> Cycle -> Int
 | 
			
		||||
computeX x (Addx2 dx) = x + dx
 | 
			
		||||
computeX x _ = x
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
drawCRT :: [Bool] -> (Int, Int) -> [Bool]
 | 
			
		||||
drawCRT crt (c,x) = sx ++ [draw] ++ (tail xs)
 | 
			
		||||
    where
 | 
			
		||||
        (sx,xs) = splitAt c crt
 | 
			
		||||
        sprite = [x-1,x,x+1]
 | 
			
		||||
        col = (c `mod` 40)
 | 
			
		||||
        draw = elem col sprite
 | 
			
		||||
 | 
			
		||||
printCRT :: [Bool] -> String
 | 
			
		||||
printCRT = concat . map (++"\n") . chunksOf 40 . map crtchr
 | 
			
		||||
    where
 | 
			
		||||
        crtchr False = '.'
 | 
			
		||||
        crtchr True  = '#'
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
handler :: String -> String
 | 
			
		||||
handler s = (show $ sum score) ++ "\n" ++
 | 
			
		||||
            (printCRT crt) ++ "\n"
 | 
			
		||||
    where
 | 
			
		||||
        cycles = parseAsm s
 | 
			
		||||
        xhs = scanl computeX 1 cycles
 | 
			
		||||
        sigstr = zipWith (*) [1..] xhs
 | 
			
		||||
        score = map ((0:sigstr) !!) [20,60..220]
 | 
			
		||||
        crt = foldl drawCRT (replicate 240 False) (zip [0..239] xhs)
 | 
			
		||||
 | 
			
		||||
main :: IO ()
 | 
			
		||||
main = do
 | 
			
		||||
    interact handler
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
		Reference in New Issue
	
	Block a user