2021-12-08 02:02:03 +00:00
|
|
|
import Parsing (splitByString)
|
|
|
|
|
|
|
|
main :: IO ()
|
|
|
|
main = do
|
|
|
|
input <- getContents
|
|
|
|
let
|
|
|
|
fish = parseFish input
|
|
|
|
(putStrLn . show . solution1) fish
|
2021-12-08 03:29:11 +00:00
|
|
|
(putStrLn . show . solution2) fish
|
2021-12-08 02:02:03 +00:00
|
|
|
|
|
|
|
solution1 :: [Int] -> Int
|
2021-12-08 03:29:11 +00:00
|
|
|
solution1 = sum . (simulateDays 79)
|
|
|
|
|
|
|
|
solution2 :: [Int] -> Int
|
|
|
|
solution2 = sum . (simulateDays 255)
|
2021-12-08 02:02:03 +00:00
|
|
|
|
|
|
|
parseFish :: String -> [Int]
|
|
|
|
parseFish = (map read) . (splitByString ",")
|
|
|
|
|
2021-12-08 03:29:11 +00:00
|
|
|
initBuffer :: [Int] -> [Int]
|
|
|
|
initBuffer initialFish = map occurrences [0..8]
|
|
|
|
where
|
|
|
|
occurrences x = length (filter (==x) initialFish)
|
2021-12-08 02:02:03 +00:00
|
|
|
|
2021-12-08 03:29:11 +00:00
|
|
|
simulateDays :: Int -> [Int] -> [Int]
|
|
|
|
simulateDays days initialFish = foldl tickDay (initBuffer initialFish) [0..days]
|
|
|
|
where
|
|
|
|
tickDay :: [Int] -> Int -> [Int]
|
|
|
|
tickDay fish day = map fishMultiplier [0..length(fish)-1]
|
|
|
|
where
|
|
|
|
fishMultiplier :: Int -> Int
|
|
|
|
fishMultiplier i
|
|
|
|
| i == addedTo =
|
|
|
|
(fish !! i) + (fish !! dayFish)
|
|
|
|
| otherwise =
|
|
|
|
fish !! i
|
|
|
|
where
|
|
|
|
dayFish = day `rem` 9
|
|
|
|
addedTo = (dayFish + 7) `rem` 9
|
2021-12-08 02:02:03 +00:00
|
|
|
|
|
|
|
-- Tests
|
|
|
|
|
|
|
|
testInput = "3,4,3,1,2"
|
|
|
|
testParsed = parseFish testInput
|
|
|
|
|
2021-12-08 03:29:11 +00:00
|
|
|
test1 = solution1 (parseFish testInput) -- 5934
|
|
|
|
test2 = solution2 (parseFish testInput) -- 26984457539
|