Extract out common Haskell utilities
Diff
2023/10.hs | 13 +++----------
2023/11.hs | 29 +++--------------------------
2023/6.hs | 13 +++----------
2023/7.hs | 13 +++----------
2023/8.hs | 13 +++----------
2023/9.hs | 13 +++----------
aoc.hs | 34 ++++++++++++++++++++++++++++++++++
7 files changed, 52 insertions(+), 76 deletions(-)
@@ -1,5 +1,5 @@
#!/usr/bin/env nix-shell
#!nix-shell #!nix-shell
import Data.List
import Data.Maybe (listToMaybe)
@@ -8,9 +8,10 @@ import Text.Parsec
import Text.Parsec.Char
import Text.Parsec.Combinator
import Text.Parsec.String (Parser)
import Aoc (readAndParseStdin)
main = do
input <- buildPipeLoop <$> readAndParseStdin
input <- buildPipeLoop <$> readAndParseStdin parseInput
print $ part1 input
print $ part2 input
@@ -98,14 +99,6 @@ findStartingPosition tiles = case listToMaybe [(x, y) | (y, row) <- zip [0 ..] t
Just v -> v
Nothing -> error "input contains no starting tile"
readAndParseStdin :: IO [[Tile]]
readAndParseStdin = do
content <- getContents
case parse parseInput "" content of
Left parseError -> error $ show parseError
Right doc -> return doc
parseInput :: Parser [[Tile]]
parseInput = parseLine `sepBy` char '\n'
@@ -1,14 +1,15 @@
#!/usr/bin/env nix-shell
#!nix-shell #!nix-shell
import Data.List (tails, transpose)
import Text.Parsec
import Text.Parsec.Char
import Text.Parsec.Combinator
import Text.Parsec.String (Parser)
import Aoc (parseGrid, readAndParseStdin)
main = do
input <- readAndParseStdin
input <- readAndParseStdin parseGrid
let expansion = findEmptySpace input
print $ part1 input expansion
print $ part2 input expansion
@@ -57,27 +58,3 @@ findEmptySpace grid = (findX grid, findY grid)
pairs :: [a] -> [(a, a)]
pairs xs = [(x, y) | (x : ys) <- tails xs, y <- ys]
readAndParseStdin :: IO [[Bool]]
readAndParseStdin = do
content <- getContents
case parse parseInput "" content of
Left parseError -> error $ show parseError
Right doc -> return doc
parseInput :: Parser [[Bool]]
parseInput = parseLine `sepBy` char '\n'
parseLine :: Parser [Bool]
parseLine = many1 parseTile
parseTile :: Parser Bool
parseTile =
choice
[ True <$ char '#',
False <$ char '.'
]
@@ -1,16 +1,17 @@
#!/usr/bin/env nix-shell
#!nix-shell -i runghc -p "haskellPackages.ghcWithPackages (pkgs: with pkgs; [ ])"
#!nix-shell
import Control.Applicative ((<*))
import Text.Parsec
import Text.Parsec.Char
import Text.Parsec.Combinator
import Text.Parsec.String (Parser)
import Aoc (readAndParseStdin)
main = do
game <- readAndParseStdin
game <- readAndParseStdin gameParser
print $ part1 game
print $ part2 game
@@ -37,14 +38,6 @@ scale n
distance :: Int -> Int -> Int
distance v t = v * (t - v)
readAndParseStdin :: IO [(Int, Int)]
readAndParseStdin = do
content <- getContents
case parse gameParser "" content of
Left parseError -> error $ show parseError
Right game -> return game
gameParser :: Parser [(Int, Int)]
gameParser = do
@@ -1,5 +1,5 @@
#!/usr/bin/env nix-shell
#!nix-shell -i runghc -p "haskellPackages.ghcWithPackages (pkgs: with pkgs; [ ])"
#!nix-shell
import Data.List
import Data.Ord
@@ -7,12 +7,13 @@ import Text.Parsec
import Text.Parsec.Char
import Text.Parsec.Combinator
import Text.Parsec.String (Parser)
import Aoc (readAndParseStdin)
main :: IO ()
main = do
games <- readAndParseStdin
games <- readAndParseStdin parseAllGames
print $ part1 games
print $ part2 games
@@ -66,14 +67,6 @@ getHandStrength sortedCardCount = case sortedCardCount of
groupCards :: [Rank] -> [Int]
groupCards = sortOn Down . map length . group . sort
readAndParseStdin :: IO [Game]
readAndParseStdin = do
content <- getContents
case parse parseAllGames "" content of
Left parseError -> error $ show parseError
Right game -> return game
parseAllGames :: Parser [Game]
parseAllGames = parseGame `endBy` char '\n'
@@ -1,5 +1,5 @@
#!/usr/bin/env nix-shell
#!nix-shell -i runghc -p "haskellPackages.ghcWithPackages (pkgs: with pkgs; [ ])"
#!nix-shell
import Data.List
import qualified Data.Map as Map
@@ -7,11 +7,12 @@ import Text.Parsec
import Text.Parsec.Char
import Text.Parsec.Combinator
import Text.Parsec.String (Parser)
import Aoc (readAndParseStdin)
main = do
document <- readAndParseStdin
document <- readAndParseStdin parseDocument
print $ part1 document
print $ part2 document
@@ -41,14 +42,6 @@ traverseTreeUntil (x : xs) m n predicate elem
readNext (n, _) DirectionLeft = n
readNext (_, n) DirectionRight = n
readAndParseStdin :: IO Document
readAndParseStdin = do
content <- getContents
case parse parseDocument "" content of
Left parseError -> error $ show parseError
Right doc -> return doc
parseDocument :: Parser Document
parseDocument = do
@@ -1,5 +1,5 @@
#!/usr/bin/env nix-shell
#!nix-shell #!nix-shell
import Control.Monad (guard)
import Data.List (unfoldr)
@@ -7,9 +7,10 @@ import Text.Parsec
import Text.Parsec.Char
import Text.Parsec.Combinator
import Text.Parsec.String (Parser)
import Aoc (readAndParseStdin)
main = do
input <- readAndParseStdin
input <- readAndParseStdin parseInput
print $ part1 input
print $ part2 input
@@ -59,14 +60,6 @@ buildDifferenceTable input = input : unfoldr buildRow input
let row = diffPairs $ zipPairs lst
in guard (not $ null row) >> Just (row, row)
readAndParseStdin :: IO [[Int]]
readAndParseStdin = do
content <- getContents
case parse parseInput "" content of
Left parseError -> error $ show parseError
Right doc -> return doc
parseInput :: Parser [[Int]]
parseInput = parseSequence `sepBy` char '\n'
@@ -0,0 +1,34 @@
module Aoc where
import Text.Parsec
import Text.Parsec.Char
import Text.Parsec.Combinator
import Text.Parsec.String (Parser)
readAndParseStdin :: Parser a -> IO a
readAndParseStdin parser = do
content <- getContents
case parse parser "" content of
Left parseError -> error $ show parseError
Right doc -> return doc
parseMultipleGrids :: Parser [[[Bool]]]
parseMultipleGrids = parseGrid `sepBy` string "\n\n"
parseGrid :: Parser [[Bool]]
parseGrid = parseGridRow `sepBy` char '\n'
parseGridRow :: Parser [Bool]
parseGridRow = many1 parseGridTile
parseGridTile :: Parser Bool
parseGridTile =
choice
[ True <$ char '#',
False <$ char '.'
]