AoC/2023/day15/day15.hs
2023-12-24 23:40:18 +01:00

40 lines
1.1 KiB
Haskell

import Control.Arrow
import Control.Lens
import Data.Function
import Data.List
import Data.List.Split
import Data.Maybe
import Text.Read
type HASH = (String, Maybe Int)
main :: IO ()
main = interact $ show . (day15a &&& day15b . parse) . init
parse :: String -> [HASH]
parse = map (second (readMaybe . tail) . break (`elem` "=-")) . splitOn ","
day15a :: String -> Int
day15a = sum . map (foldl' hashAlg 0) . splitOn ","
day15b :: [HASH] -> Int
day15b =
sum .
zipWith (*) [1 ..] .
map (sum . zipWith (*) [1 ..] . map (fromJust . snd)) .
foldl' processInstruction (replicate 256 [])
hashAlg :: Int -> Char -> Int
hashAlg x y = (17 * (fromEnum y + x)) `mod` 256
processInstruction :: [[HASH]] -> HASH -> [[HASH]]
processInstruction bs (s, action) = (element box .~ l) bs
where
mInsert x = uncurry (++) . second (f x) . break (((==) `on` fst) x)
f a (_:xs) = a : xs
f a [] = [a]
box = foldl' hashAlg 0 s
newList = mInsert (s, action) (bs !! box)
newDelList = deleteBy ((==) `on` fst) (s, action) (bs !! box)
l = maybe newDelList (const newList) action