Day 4
This commit is contained in:
parent
e9187a27db
commit
d3d933d2a9
1 changed files with 79 additions and 0 deletions
79
src/Day2504.hs
Normal file
79
src/Day2504.hs
Normal file
|
|
@ -0,0 +1,79 @@
|
||||||
|
module Main where
|
||||||
|
|
||||||
|
import Debug.Trace (trace)
|
||||||
|
|
||||||
|
guard :: Bool -> [()]
|
||||||
|
guard True = [()]
|
||||||
|
guard False = []
|
||||||
|
|
||||||
|
gridMap :: (a -> b) -> [[a]] -> [[b]]
|
||||||
|
gridMap f = map (map f)
|
||||||
|
|
||||||
|
gridMapWithIndex :: ((Int, Int) -> a -> b) -> [[a]] -> [[b]]
|
||||||
|
gridMapWithIndex f grid = map (\(y, row) -> map (\(x, cell) -> (f (x,y) cell)) $ zip [0..] row) $ zip [0..] grid
|
||||||
|
|
||||||
|
--------------------
|
||||||
|
----- Problems -----
|
||||||
|
--------------------
|
||||||
|
|
||||||
|
isReachable :: [String] -> (Int, Int) -> Bool
|
||||||
|
isReachable input (x,y) = let
|
||||||
|
w = length (head input)
|
||||||
|
h = length input
|
||||||
|
in ((< (4+1)) . length) $ do
|
||||||
|
dy <- [-1..1]
|
||||||
|
dx <- [-1..1]
|
||||||
|
|
||||||
|
let ax = dx+x
|
||||||
|
let ay = dy+y
|
||||||
|
|
||||||
|
guard $ (ax >= 0 && ax < w && ay >= 0 && ay < h)
|
||||||
|
|
||||||
|
guard $ (input!!(y+dy))!!(x+dx) == '@'
|
||||||
|
|
||||||
|
return ()
|
||||||
|
|
||||||
|
part1 :: String -> Int
|
||||||
|
part1 str = length $ filter id a
|
||||||
|
where
|
||||||
|
w = length (head input)
|
||||||
|
h = length input
|
||||||
|
|
||||||
|
input = lines str
|
||||||
|
a = do
|
||||||
|
y <- [0..w-1]
|
||||||
|
x <- [0..h-1]
|
||||||
|
|
||||||
|
guard $ (input!!y)!!x == '@'
|
||||||
|
|
||||||
|
return $ isReachable input (x,y)
|
||||||
|
|
||||||
|
part2 :: String -> Int
|
||||||
|
part2 str = go grid
|
||||||
|
where
|
||||||
|
grid = lines str
|
||||||
|
w = length (head grid)
|
||||||
|
h = length grid
|
||||||
|
|
||||||
|
countBoxes = length . filter id . concat . gridMap (\c -> if c=='@' then True else False)
|
||||||
|
|
||||||
|
go :: [[Char]] -> Int
|
||||||
|
go grid | startCount == endCount = 0
|
||||||
|
| otherwise = (startCount - endCount) + go end
|
||||||
|
where
|
||||||
|
startCount = countBoxes grid
|
||||||
|
end = iter grid
|
||||||
|
endCount = countBoxes end
|
||||||
|
|
||||||
|
iter :: [[Char]] -> [[Char]]
|
||||||
|
iter input = gridMapWithIndex select input
|
||||||
|
where
|
||||||
|
select = \(x,y) c -> if c == '@' then if isReachable input (x,y) then '.' else '@' else c
|
||||||
|
|
||||||
|
|
||||||
|
main :: IO ()
|
||||||
|
main = do
|
||||||
|
str <- getContents
|
||||||
|
|
||||||
|
print $ part1 str
|
||||||
|
print $ part2 str
|
||||||
Loading…
Add table
Add a link
Reference in a new issue