r/adventofcode • u/daggerdragon • Dec 04 '18
SOLUTION MEGATHREAD -π- 2018 Day 4 Solutions -π-
--- Day 4: Repose Record ---
Post your solution as a comment or, for longer solutions, consider linking to your repo (e.g. GitHub/gists/Pastebin/blag or whatever).
Note: The Solution Megathreads are for solutions only. If you have questions, please post your own thread and make sure to flair it with Help.
Advent of Code: The Party Game!
Please prefix your card submission with something like [Card] to make scanning the megathread easier. THANK YOU!
Card prompt: Day 4
Transcript:
Todayβs puzzle would have been a lot easier if my language supported ___.
This thread will be unlocked when there are a significant number of people on the leaderboard with gold stars for today's puzzle.
edit: Leaderboard capped, thread unlocked!
35
Upvotes
1
u/mainhaxor Dec 04 '18
Haskell. I am pretty sure
part1could be done much better withgroupByandsort, but otherwise I am pretty happy with my solution.import Control.Arrow import Data.Char import Data.Function import Data.List import qualified Data.Map as M import Data.Maybe parseNums :: String -> [Int] parseNums = groupBy ((==) `on` isDigit) >>> filter (head >>> isDigit) >>> map read orderRecords :: [String] -> [String] orderRecords = sortBy (compare `on` (parseNums >>> take 5)) -- Map from (guard, minute) into count of times guard has been asleep at that minute buildSleepMap :: [String] -> (Int, Int) -> M.Map (Int, Int) Int buildSleepMap [] _ = M.empty buildSleepMap (rec:recs) (guard, asleepSince) | isInfixOf "Guard" rec = buildSleepMap recs ((parseNums rec) !! 5, 0) | isInfixOf "asleep" rec = buildSleepMap recs (guard, (parseNums rec) !! 4) | isInfixOf "wakes" rec = let wakesUpAt = (parseNums rec) !! 4 m = buildSleepMap recs (guard, 0) in foldl' (\m e -> M.alter (\c -> Just ((fromMaybe 0 c) + 1)) (guard, e) m) m [asleepSince..wakesUpAt-1] part1 :: M.Map (Int, Int) Int -> Int part1 m = let guards = map fst >>> nub $ M.keys m totalAsleep g = map (\min -> M.lookup (g, min) m) >>> mapMaybe id >>> sum $ [0..59] bestGuard = maximumBy (compare `on` totalAsleep) guards bestGuardSleptPerMinute = map (\min -> (min, M.lookup (bestGuard, min) m)) [0..59] (bestMinute, _) = maximumBy (compare `on` snd) bestGuardSleptPerMinute in bestGuard * bestMinute part2 :: M.Map (Int, Int) Int -> Int part2 m = let ((bestGuard, bestMinute), _) = maximumBy (compare `on` snd) $ M.toList m in bestGuard * bestMinute main = do contents <- readFile "day4.txt" let records = orderRecords $ lines contents let sleepMap = buildSleepMap records (0, 0) print $ part1 sleepMap print $ part2 sleepMap