41 lines
1.1 KiB
Haskell
41 lines
1.1 KiB
Haskell
main :: IO ()
|
|
main = readFile "2/input.txt" >>= print . solve . parse . lines
|
|
|
|
parse :: [String] -> [Instruction]
|
|
parse = map (parseLine . words)
|
|
|
|
solve :: [Instruction] -> (Int,Int)
|
|
solve input = (f input, g input)
|
|
where f = uncurry (*) . simulate Abs
|
|
g = uncurry (*) . simulate (Aim 0)
|
|
|
|
data Nav = Aim Int
|
|
| Abs
|
|
|
|
data Instruction = Forward Int
|
|
| Down Int
|
|
| Up Int
|
|
|
|
parseLine :: [String] -> Instruction
|
|
parseLine [ s, x ]
|
|
| s == "forward" = Forward n
|
|
| s == "down" = Down n
|
|
| s == "up" = Up n
|
|
where
|
|
n = read x
|
|
|
|
simulate :: Nav -> [Instruction] -> (Int,Int)
|
|
simulate nav = iter nav (0,0)
|
|
|
|
iter :: Nav -> (Int,Int) -> [Instruction] -> (Int,Int)
|
|
iter _ r [] = r
|
|
iter Abs (x,y) (i:is) = case i of
|
|
Forward n -> iter Abs (x+n,y)
|
|
Down n -> iter Abs (x,y+n)
|
|
Up n -> iter Abs (x,y-n)
|
|
$ is
|
|
iter (Aim a) (x,y) (i:is) = case i of
|
|
Forward n -> iter (Aim a) (x+n,y+(a*n))
|
|
Down n -> iter (Aim (a+n)) (x,y)
|
|
Up n -> iter (Aim (a-n)) (x,y)
|
|
$ is
|