diff --git a/solutions/solutions.cabal b/solutions/solutions.cabal index d37cfce..1874819 100644 --- a/solutions/solutions.cabal +++ b/solutions/solutions.cabal @@ -1003,7 +1003,7 @@ executable sln_2023_02 executable sln_2023_03 import: day main-is: 2023/03.hs - build-depends: containers + build-depends: array, containers executable sln_2023_04 import: day @@ -1035,7 +1035,7 @@ executable sln_2023_09 executable sln_2023_10 import: day main-is: 2023/10.hs - build-depends: containers + build-depends: array executable sln_2023_11 import: day diff --git a/solutions/src/2022/23.hs b/solutions/src/2022/23.hs index 018c83c..d24f785 100644 --- a/solutions/src/2022/23.hs +++ b/solutions/src/2022/23.hs @@ -22,16 +22,16 @@ Maintainer : emertens@gmail.com 20 -} -module Main where +module Main (main) where -import Data.Array.Unboxed (Ix(rangeSize), UArray, accumArray) +import Data.Array.Unboxed (UArray, assocs, rangeSize, UArray, accumArray) import Data.List (foldl', tails) import Data.Map qualified as Map import Data.Maybe (fromMaybe) import Data.Set (Set) import Data.Set qualified as Set -import Advent (arrIx, getInputMap) +import Advent (arrIx, getInputArray) import Advent.Coord (Coord, above, below, boundingBox, left, neighbors, right) -- | @@ -40,7 +40,8 @@ import Advent.Coord (Coord, above, below, boundingBox, left, neighbors, right) -- 1023 main :: IO () main = - do elves <- Map.keysSet . Map.filter ('#'==) <$> getInputMap 2022 23 + do input <- getInputArray 2022 23 + let elves = Set.fromList [c | (c, '#') <- assocs input] let states = sim elves -- part 1 diff --git a/solutions/src/2023/03.hs b/solutions/src/2023/03.hs index 68ad186..28914bf 100644 --- a/solutions/src/2023/03.hs +++ b/solutions/src/2023/03.hs @@ -27,12 +27,12 @@ Maintainer : emertens@gmail.com -} module Main (main) where -import Data.Map (Map) -import Data.Map qualified as Map -import Data.Char (isDigit) - -import Advent (getInputMap, ordNub) +import Advent (getInputArray, ordNub, arrIx) import Advent.Coord (Coord, left, neighbors, right) +import Data.Array.Unboxed (UArray, assocs) +import Data.Char (isDigit) +import Data.Map qualified as Map +import Data.Maybe (fromMaybe) -- | Parse the input schematic and print answers to both parts. -- @@ -41,21 +41,21 @@ import Advent.Coord (Coord, left, neighbors, right) -- 81463996 main :: IO () main = - do input <- getInputMap 2023 3 + do input <- getInputArray 2023 3 let numbers = extractNumbers input print (sum [partNo | (partNo, _:_) <- numbers]) print (sum [a * b | [a, b] <- gearNumbers numbers]) -- | Extract the numbers from the diagram and the parts adjacent to them. -extractNumbers :: Map Coord Char -> [(Int, [(Coord, Char)])] +extractNumbers :: UArray Coord Char -> [(Int, [(Coord, Char)])] extractNumbers input = [ (read digits, partsNear cs) - | (c, digit) <- Map.assocs input + | (c, digit) <- assocs input , isDigit digit, not (isDigit (lkp (left c))) -- left-boundary of number , let (cs, digits) = unzip (numbersAfter c) ] where - lkp i = Map.findWithDefault '.' i input + lkp = fromMaybe '.' . arrIx input numbersAfter start = [ (c, digit) | c <- iterate right start diff --git a/solutions/src/2023/07.hs b/solutions/src/2023/07.hs index 2096a70..9030388 100644 --- a/solutions/src/2023/07.hs +++ b/solutions/src/2023/07.hs @@ -28,12 +28,12 @@ module Main (main) where import Advent (format, counts) import Data.Foldable (toList) -import Data.List (sortOn, sortBy, elemIndex, nub) +import Data.List (sortOn, sortBy, elemIndex) import Data.Maybe (fromJust) import Data.Map (Map) import Data.Map qualified as Map --- | +-- | Parse the input hands and print the answers to both parts. -- -- >>> :main -- 248422077 diff --git a/solutions/src/2023/10.hs b/solutions/src/2023/10.hs index f4de090..d17adbc 100644 --- a/solutions/src/2023/10.hs +++ b/solutions/src/2023/10.hs @@ -60,11 +60,9 @@ L7JLJL-JLJLJL--JLJ.L -} module Main (main) where -import Advent (getInputMap) +import Advent (getInputArray, arrIx) import Advent.Coord (invert, invert', south, north, west, Coord(C)) -import Advent.Search (dfsOn) -import Data.Map (Map) -import Data.Map qualified as Map +import Data.Array.Unboxed (UArray, (!), assocs) -- | Parse the input and print out answers to both parts. -- @@ -73,29 +71,30 @@ import Data.Map qualified as Map -- 541 main :: IO () main = - do input <- getInputMap 2023 10 + do input <- getInputArray 2023 10 let (start, dir0) = pickStart input route = getLoop (map fst (iterate (step input) (start, dir0))) perimeter = length route print (perimeter `quot` 2) print (abs (polyareaRect route) - perimeter `quot` 2 + 1) -pickStart :: Map Coord Char -> (Coord, Coord) +pickStart :: UArray Coord Char -> (Coord, Coord) pickStart input = head [ (k, dir) - | (k, 'S') <- Map.assocs input + | (k, 'S') <- assocs input , (dir, ok) <- [(south, "L|J"), (north, "F|7"), (west,"7-J")] - , let next = Map.findWithDefault '.' (k + dir) input + , next <- arrIx input (k + dir) , next `elem` ok ] getLoop :: Eq a => [a] -> [a] getLoop (x:xs) = x : takeWhile (x /=) xs +getLoop [] = error "getLoop: empty input" -step :: Map Coord Char -> (Coord, Coord) -> (Coord, Coord) +step :: UArray Coord Char -> (Coord, Coord) -> (Coord, Coord) step inp (here, dir) = let here' = here + dir in - (here', pipeEffect (inp Map.! here') dir) + (here', pipeEffect (inp ! here') dir) pipeEffect :: Char -> Coord -> Coord pipeEffect = \case