Advent of Code 2025
at main 1.2 kB view raw
1module Day5 where 2 3import Debug.Trace 4import Data.Char 5import Data.List 6import Util 7 8type Range = (Int,Int) 9 10parse :: String -> ([Range], [Int]) 11parse s = foldl addLine ([], []) $ map (map read) $ map (splitOn (not . isDigit)) $ lines s 12 where addLine (ranges, queries) [lhs, rhs] = ((lhs, rhs) : ranges, queries) 13 addLine (ranges, queries) [q] = (ranges, q : queries) 14 addLine (ranges, queries) [] = (ranges, queries) 15 16inRange :: Range -> Int -> Bool 17inRange (lo,hi) q = lo <= q && q <= hi 18 19inRanges :: [Range] -> Int -> Bool 20inRanges rs q = any (\r -> inRange r q) rs 21 22part1 :: String -> String 23part1 input = 24 let (rs,qs) = parse input 25 in show $ 26 length $ 27 filter (inRanges rs) qs 28 29rangeUnion :: [Range] -> [Range] 30rangeUnion rs = 31 let mergeWith cur [] = [cur] 32 mergeWith (lo,hi) ((lo',hi') : rest) = 33 if lo' <= hi then 34 mergeWith (lo, max hi hi') rest 35 else 36 (lo, hi) : mergeWith (lo', hi') rest 37 38 merge [] = [] 39 merge (r : rest) = mergeWith r rest 40 in merge $ sort rs 41 42part2 :: String -> String 43part2 input = 44 let (rs, _) = parse input 45 in show $ 46 sum $ 47 map (\(a,b) -> b-a+1) $ 48 rangeUnion rs