From 6e14034432304362e9c39dd2142ece455306c9e3 Mon Sep 17 00:00:00 2001 From: ctsk <9384305+ctsk@users.noreply.github.com> Date: Mon, 18 Sep 2023 08:07:05 +0200 Subject: [PATCH] Day 9 --- .gitignore | 4 +- Y2022.cabal | 7 +- app/Main.hs | 1 + bench/Bench.hs | 1 + data/09.in | 2000 +++++++++++++++++++++++++++++++++++++++++++++++ src/Days/D09.hs | 110 +++ src/Lib.hs | 2 + 7 files changed, 2122 insertions(+), 3 deletions(-) create mode 100644 data/09.in create mode 100644 src/Days/D09.hs diff --git a/.gitignore b/.gitignore index 82fdd79..f4fd317 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,3 @@ -/dist-newstyle \ No newline at end of file +/.vscode +/dist-newstyle +/*.prof \ No newline at end of file diff --git a/Y2022.cabal b/Y2022.cabal index d5cc680..9e8d7af 100644 --- a/Y2022.cabal +++ b/Y2022.cabal @@ -42,12 +42,15 @@ library Days.D06 Days.D07 Days.D08 + Days.D09 build-depends: bytestring - , megaparsec ^>=9.4.0 + , megaparsec ^>=9.4.0 , mtl + , hashable + , hashtables ^>=1.3.1 , text - , vector ^>=0.13.0.0 + , vector ^>=0.13.0.0 executable Y2022 import: warnings, defaults diff --git a/app/Main.hs b/app/Main.hs index 1e4e6c9..22d09a1 100644 --- a/app/Main.hs +++ b/app/Main.hs @@ -16,6 +16,7 @@ paths = , "./data/06.in" , "./data/07.in" , "./data/08.in" + , "./data/09.in" ] solutions :: [(Int, Day, FilePath)] diff --git a/bench/Bench.hs b/bench/Bench.hs index 54afe0a..f429839 100644 --- a/bench/Bench.hs +++ b/bench/Bench.hs @@ -15,6 +15,7 @@ paths = , "./data/06.in" , "./data/07.in" , "./data/08.in" + , "./data/09.in" ] solutions :: [(Integer, [Day], FilePath)] diff --git a/data/09.in b/data/09.in new file mode 100644 index 0000000..e54f034 --- /dev/null +++ b/data/09.in @@ -0,0 +1,2000 @@ +U 1 +R 2 +D 1 +L 1 +U 2 +D 1 +U 2 +L 1 +D 1 +U 2 +R 1 +U 1 +D 1 +R 1 +L 2 +D 1 +U 1 +D 1 +U 2 +D 2 +R 2 +D 1 +R 2 +D 2 +R 1 +L 2 +U 2 +D 2 +R 2 +D 1 +R 1 +L 1 +D 2 +U 2 +L 2 +U 2 +R 1 +L 1 +D 1 +R 1 +D 2 +U 1 +L 2 +R 1 +U 1 +D 1 +U 1 +D 2 +R 1 +L 1 +U 1 +L 1 +R 2 +U 1 +R 2 +L 2 +U 1 +R 1 +L 2 +R 2 +L 2 +U 1 +D 1 +U 2 +R 1 +D 1 +L 2 +D 1 +L 1 +U 1 +R 2 +U 1 +D 1 +L 2 +R 2 +D 2 +R 2 +D 1 +L 2 +D 1 +R 2 +L 1 +D 2 +R 2 +D 1 +U 1 +L 1 +R 2 +L 2 +D 1 +R 1 +L 1 +U 1 +L 1 +R 1 +U 2 +R 1 +D 2 +R 1 +L 2 +R 1 +L 1 +D 2 +R 2 +L 1 +U 1 +D 1 +L 2 +D 1 +L 1 +R 1 +U 1 +R 3 +U 2 +L 2 +R 1 +L 1 +D 1 +R 1 +U 2 +D 3 +L 1 +R 1 +U 2 +R 1 +U 1 +R 3 +L 3 +U 2 +D 1 +L 1 +R 1 +U 3 +D 1 +L 3 +D 2 +U 3 +R 3 +D 1 +L 3 +D 1 +U 1 +R 3 +L 2 +U 1 +R 3 +U 3 +L 3 +D 1 +R 2 +U 3 +R 2 +L 1 +U 3 +L 3 +R 3 +D 2 +U 1 +L 1 +D 1 +U 3 +D 1 +U 2 +R 1 +L 2 +R 2 +L 2 +D 3 +R 2 +D 2 +U 1 +L 2 +R 2 +L 1 +U 3 +D 3 +R 1 +L 1 +D 3 +L 2 +U 2 +R 3 +L 1 +D 2 +L 1 +R 2 +L 2 +U 2 +D 3 +R 2 +U 3 +D 1 +L 2 +D 3 +U 1 +R 3 +U 1 +R 2 +U 2 +D 1 +L 1 +D 3 +L 2 +U 1 +R 1 +L 1 +U 2 +D 3 +U 3 +R 3 +U 1 +R 1 +D 2 +R 1 +L 2 +D 2 +U 1 +R 3 +D 2 +U 2 +L 2 +R 3 +D 2 +U 1 +R 1 +L 3 +R 1 +U 1 +R 4 +L 2 +R 3 +D 3 +L 3 +D 3 +R 3 +L 2 +R 4 +D 1 +R 2 +U 3 +D 4 +U 2 +R 4 +U 2 +R 3 +L 2 +D 1 +U 3 +D 1 +L 4 +U 4 +D 4 +R 2 +U 1 +L 2 +R 2 +L 4 +R 3 +U 4 +D 3 +R 2 +L 2 +R 2 +D 2 +U 1 +R 2 +U 3 +R 4 +D 1 +L 4 +U 2 +R 3 +U 3 +R 4 +L 1 +D 3 +R 3 +D 4 +R 2 +L 3 +R 1 +D 4 +R 2 +L 2 +U 3 +R 3 +U 2 +R 3 +U 4 +R 1 +L 1 +D 4 +U 4 +D 3 +L 1 +D 3 +L 2 +U 2 +R 2 +D 3 +R 2 +U 1 +R 4 +D 3 +L 2 +D 1 +L 4 +D 1 +R 4 +D 4 +R 1 +U 3 +L 2 +U 1 +R 3 +U 2 +L 3 +D 1 +U 4 +L 2 +D 1 +L 2 +R 3 +U 4 +R 1 +U 1 +L 3 +U 4 +D 3 +L 2 +D 1 +L 3 +R 2 +D 4 +L 1 +D 5 +U 4 +D 2 +R 1 +D 3 +L 3 +R 1 +D 5 +U 3 +D 5 +L 2 +D 1 +L 3 +R 5 +U 4 +L 3 +D 4 +U 5 +D 5 +L 2 +U 5 +L 2 +R 3 +L 1 +U 2 +D 4 +R 3 +D 4 +U 5 +D 3 +U 4 +L 4 +R 1 +L 5 +U 5 +R 2 +U 4 +R 3 +D 1 +U 1 +R 2 +U 4 +R 2 +D 2 +U 1 +R 1 +L 2 +D 1 +U 5 +L 4 +R 2 +D 1 +U 1 +D 2 +U 2 +D 5 +L 2 +R 5 +U 5 +L 5 +D 2 +L 1 +U 3 +D 1 +R 3 +D 2 +L 3 +R 3 +D 3 +R 2 +L 1 +D 1 +U 2 +R 2 +L 2 +R 5 +U 4 +D 3 +L 4 +U 4 +D 1 +U 4 +D 2 +U 5 +L 4 +R 5 +D 4 +R 2 +D 2 +R 5 +D 4 +U 1 +D 3 +U 5 +R 3 +D 2 +R 5 +L 1 +U 5 +R 5 +U 1 +R 3 +U 3 +R 4 +U 1 +L 4 +R 1 +U 3 +L 2 +U 6 +D 4 +U 3 +D 1 +R 2 +L 6 +U 3 +D 4 +U 1 +L 6 +U 1 +R 1 +U 6 +D 5 +U 5 +R 4 +U 1 +L 4 +D 1 +U 5 +R 3 +L 2 +U 3 +L 6 +R 5 +U 4 +R 5 +D 1 +L 6 +U 3 +L 5 +U 2 +L 5 +R 2 +U 6 +R 6 +D 1 +R 1 +U 3 +R 6 +U 5 +L 4 +U 2 +R 5 +L 2 +U 1 +D 1 +U 5 +R 2 +U 2 +L 4 +R 2 +D 1 +L 4 +U 1 +L 6 +R 6 +U 2 +D 5 +U 5 +D 4 +L 1 +R 3 +L 5 +U 6 +R 4 +D 1 +U 2 +R 1 +D 3 +R 1 +L 5 +D 3 +R 3 +U 5 +L 6 +R 3 +U 5 +L 2 +U 3 +R 3 +D 3 +U 1 +L 2 +U 2 +L 3 +D 6 +L 3 +D 4 +R 4 +D 4 +U 6 +L 6 +D 2 +R 1 +U 3 +L 6 +R 4 +D 1 +L 2 +U 4 +L 6 +U 1 +L 4 +D 1 +L 3 +R 2 +L 1 +R 2 +L 3 +R 1 +U 7 +D 7 +L 7 +U 1 +R 2 +U 6 +R 4 +L 6 +U 3 +R 4 +U 7 +D 5 +R 6 +U 6 +L 6 +R 4 +D 1 +U 3 +R 5 +L 2 +D 2 +U 5 +L 1 +D 3 +R 5 +L 2 +U 4 +D 1 +R 5 +U 2 +R 4 +L 3 +R 4 +L 2 +D 2 +L 4 +D 1 +U 4 +D 4 +R 4 +L 5 +R 2 +D 2 +L 2 +D 1 +L 2 +D 1 +L 4 +D 5 +R 7 +U 7 +L 2 +D 3 +L 4 +R 7 +D 7 +U 2 +D 7 +L 6 +D 3 +U 5 +R 5 +D 3 +U 7 +D 3 +L 5 +D 3 +R 4 +D 4 +L 7 +D 6 +U 2 +L 3 +R 6 +U 5 +R 7 +U 3 +L 1 +R 7 +U 2 +R 4 +L 7 +U 2 +D 4 +U 5 +D 6 +U 4 +D 6 +U 7 +R 1 +L 4 +R 3 +L 6 +U 4 +R 7 +L 6 +U 7 +D 1 +U 7 +D 4 +L 1 +D 3 +R 6 +U 3 +R 5 +L 4 +R 4 +L 4 +U 7 +R 3 +L 4 +D 7 +R 6 +U 2 +L 3 +U 8 +D 3 +U 4 +D 1 +R 4 +U 5 +R 2 +U 4 +D 8 +L 2 +D 8 +R 4 +L 1 +R 7 +L 6 +U 4 +L 4 +D 7 +L 3 +D 2 +U 8 +R 8 +U 6 +R 7 +D 3 +U 7 +R 1 +L 8 +D 2 +L 3 +R 5 +D 3 +U 3 +R 8 +L 1 +R 6 +L 8 +U 2 +D 4 +R 6 +L 6 +D 5 +U 4 +L 6 +U 1 +L 6 +U 3 +D 5 +U 5 +L 6 +D 8 +R 5 +D 4 +R 6 +U 7 +L 1 +D 2 +R 2 +L 7 +R 4 +D 7 +L 3 +U 6 +R 7 +D 3 +L 3 +D 2 +U 1 +R 3 +L 8 +U 8 +D 5 +L 6 +R 3 +L 6 +D 3 +R 4 +U 3 +L 8 +D 7 +L 6 +R 5 +D 6 +R 6 +D 3 +L 4 +R 1 +D 6 +U 3 +R 1 +D 5 +U 4 +L 1 +R 2 +U 6 +D 6 +R 7 +L 1 +R 6 +U 7 +D 8 +R 2 +U 3 +L 6 +U 2 +D 6 +U 8 +L 3 +U 4 +D 6 +R 6 +L 5 +U 9 +R 8 +L 2 +D 6 +R 3 +L 4 +D 2 +L 7 +D 5 +L 7 +U 8 +D 6 +L 9 +D 3 +L 5 +U 3 +L 8 +D 7 +R 8 +U 2 +L 9 +U 7 +D 7 +U 6 +D 5 +R 2 +D 8 +R 9 +U 4 +R 1 +L 3 +D 7 +R 2 +L 6 +U 1 +L 7 +D 8 +U 9 +R 9 +D 1 +U 9 +D 1 +R 1 +D 6 +R 7 +D 1 +L 1 +R 6 +U 3 +R 7 +U 2 +R 5 +U 6 +R 2 +L 7 +R 8 +D 9 +U 5 +L 9 +R 9 +U 2 +L 7 +R 4 +U 3 +R 6 +L 6 +D 7 +L 4 +R 7 +D 5 +L 5 +D 7 +U 8 +R 8 +L 8 +R 5 +D 5 +U 2 +R 1 +U 5 +R 6 +L 8 +U 9 +R 4 +D 9 +R 4 +D 3 +U 8 +R 8 +U 9 +L 6 +D 9 +R 6 +U 5 +R 1 +U 1 +L 9 +U 8 +L 1 +U 5 +L 1 +D 7 +R 6 +U 1 +D 3 +R 2 +D 3 +R 8 +D 2 +U 4 +R 8 +L 9 +D 2 +U 2 +R 4 +D 10 +L 4 +U 3 +D 6 +R 4 +U 8 +L 8 +U 3 +L 10 +D 7 +U 2 +L 6 +R 2 +U 8 +L 10 +U 7 +D 8 +L 7 +U 10 +R 4 +U 1 +L 1 +D 4 +U 10 +D 9 +U 4 +L 10 +R 4 +D 5 +U 8 +D 1 +R 5 +D 10 +L 8 +D 1 +U 2 +L 7 +U 1 +L 6 +D 2 +R 3 +L 3 +U 5 +R 9 +U 10 +D 5 +U 7 +L 3 +R 5 +U 7 +L 4 +U 1 +D 2 +U 8 +L 8 +U 7 +R 9 +L 1 +D 10 +R 8 +L 4 +U 4 +L 10 +R 2 +L 3 +D 7 +L 10 +R 6 +U 5 +D 4 +U 6 +R 10 +D 8 +U 3 +L 1 +R 1 +D 2 +R 1 +U 1 +R 5 +U 9 +R 6 +U 10 +L 2 +U 5 +L 7 +R 8 +U 10 +D 6 +L 3 +U 2 +L 4 +R 6 +L 5 +D 9 +U 3 +D 3 +R 10 +L 10 +D 4 +R 7 +D 7 +U 3 +L 5 +R 5 +L 9 +R 2 +U 8 +R 10 +U 10 +L 4 +U 1 +D 2 +U 5 +L 11 +R 3 +L 10 +U 7 +D 6 +U 11 +D 11 +U 2 +L 7 +D 11 +U 8 +L 5 +U 7 +L 10 +D 7 +L 2 +U 5 +D 4 +R 9 +L 10 +D 1 +U 6 +R 2 +L 7 +U 1 +R 4 +D 11 +U 2 +R 9 +U 11 +R 6 +U 9 +L 9 +D 3 +R 6 +L 4 +R 1 +L 5 +R 2 +U 3 +R 1 +U 7 +D 1 +R 11 +L 2 +D 7 +L 10 +U 1 +R 8 +L 6 +U 7 +D 11 +R 1 +U 11 +L 8 +D 6 +R 6 +D 10 +U 2 +D 1 +L 6 +R 9 +L 8 +U 10 +R 4 +U 4 +R 9 +D 3 +R 8 +D 11 +L 4 +U 8 +D 6 +R 1 +U 5 +L 8 +U 6 +R 9 +U 1 +R 8 +D 6 +R 4 +D 7 +R 7 +L 1 +D 6 +L 3 +D 9 +L 10 +D 5 +U 10 +L 11 +D 5 +U 9 +R 10 +L 11 +R 1 +U 6 +L 4 +U 7 +R 9 +L 10 +D 9 +R 5 +L 2 +D 1 +U 12 +L 7 +D 9 +U 8 +R 12 +L 11 +D 12 +L 4 +D 10 +U 7 +L 5 +U 6 +L 5 +R 3 +L 9 +U 7 +L 8 +U 10 +L 8 +R 1 +U 3 +D 6 +L 12 +U 6 +D 7 +L 7 +U 2 +D 8 +U 10 +L 12 +R 5 +L 7 +R 11 +D 5 +L 2 +R 10 +L 7 +U 9 +D 6 +R 3 +U 9 +L 1 +U 2 +D 9 +U 1 +D 2 +L 11 +R 4 +D 4 +L 6 +R 10 +L 6 +U 10 +L 2 +D 3 +R 12 +L 5 +R 5 +L 9 +D 6 +R 12 +U 6 +R 6 +D 6 +R 3 +L 12 +D 12 +L 10 +R 7 +U 7 +L 8 +R 6 +L 5 +D 3 +L 5 +U 12 +L 6 +U 10 +D 11 +U 11 +D 1 +U 9 +R 8 +L 8 +U 5 +R 3 +L 4 +R 6 +U 10 +L 1 +D 1 +R 7 +D 8 +L 1 +D 6 +R 3 +U 2 +D 4 +L 10 +D 9 +L 12 +U 6 +D 9 +U 8 +D 8 +L 8 +U 1 +D 6 +U 6 +D 4 +R 9 +L 5 +U 6 +R 7 +U 6 +D 3 +U 6 +D 10 +U 1 +L 13 +D 4 +U 6 +L 10 +R 6 +D 7 +U 9 +R 2 +L 5 +D 4 +U 10 +D 7 +L 12 +D 2 +R 1 +D 4 +R 1 +U 6 +L 9 +D 12 +U 8 +L 6 +U 4 +R 2 +L 1 +D 12 +U 12 +L 1 +D 7 +L 3 +R 10 +L 10 +U 2 +D 8 +R 5 +U 2 +L 5 +R 8 +L 5 +D 9 +L 11 +U 1 +D 6 +R 11 +D 11 +L 6 +R 13 +L 8 +U 7 +R 11 +L 9 +D 5 +L 2 +U 1 +D 13 +R 3 +D 2 +R 9 +U 3 +R 8 +D 10 +U 5 +D 3 +L 2 +D 9 +R 10 +D 4 +U 13 +D 10 +U 2 +R 8 +D 9 +R 13 +U 4 +D 3 +L 6 +U 8 +L 3 +R 3 +D 4 +U 6 +L 7 +R 3 +L 1 +D 1 +R 5 +U 8 +D 8 +U 11 +R 5 +U 2 +R 10 +L 3 +D 4 +U 1 +R 9 +L 7 +R 6 +L 13 +U 8 +L 8 +D 5 +R 10 +L 9 +U 7 +L 9 +U 9 +L 7 +R 5 +L 5 +U 7 +D 12 +U 7 +D 6 +R 14 +D 5 +L 11 +R 6 +L 4 +U 8 +R 9 +U 7 +R 12 +L 10 +U 10 +L 11 +R 7 +D 11 +R 7 +L 4 +D 9 +L 13 +R 6 +L 13 +D 2 +R 13 +D 12 +R 4 +U 11 +R 4 +D 3 +R 3 +L 12 +R 3 +D 11 +R 7 +D 7 +R 3 +U 4 +R 12 +D 14 +R 3 +L 10 +U 9 +L 2 +U 14 +L 2 +D 7 +U 10 +D 4 +U 6 +L 1 +D 11 +R 10 +D 1 +L 2 +U 9 +L 6 +R 12 +D 11 +R 8 +U 7 +D 2 +U 4 +D 12 +L 1 +U 8 +D 14 +R 2 +D 13 +R 10 +D 10 +R 14 +L 4 +D 14 +L 6 +R 13 +L 12 +U 4 +R 13 +L 12 +D 14 +L 1 +U 1 +L 4 +D 14 +R 12 +D 6 +U 11 +L 12 +U 2 +R 8 +D 14 +U 13 +D 6 +L 7 +D 4 +U 3 +L 8 +U 2 +D 12 +L 13 +U 8 +R 4 +D 10 +L 10 +U 5 +D 3 +L 10 +D 13 +R 15 +U 9 +L 10 +D 1 +U 11 +D 7 +U 3 +R 6 +L 11 +D 4 +R 8 +D 3 +U 7 +D 6 +L 11 +D 14 +R 15 +L 14 +D 2 +L 11 +R 13 +U 4 +D 13 +L 6 +D 4 +L 15 +D 5 +L 6 +U 8 +R 13 +L 5 +U 4 +R 9 +L 13 +D 3 +U 11 +R 6 +L 14 +R 9 +U 5 +D 5 +U 9 +D 12 +R 11 +U 8 +D 1 +R 2 +U 6 +R 11 +L 4 +R 7 +D 6 +U 6 +D 1 +L 4 +R 14 +D 11 +R 3 +U 9 +D 15 +L 14 +D 9 +R 4 +U 14 +R 3 +L 14 +D 15 +L 12 +R 5 +D 6 +U 15 +D 13 +U 10 +R 4 +D 3 +R 11 +U 11 +R 4 +L 1 +D 11 +U 14 +D 1 +U 14 +R 1 +L 14 +D 4 +U 12 +D 9 +L 13 +U 10 +D 14 +L 4 +U 15 +L 12 +U 3 +D 6 +U 1 +D 2 +R 13 +L 12 +U 2 +L 12 +D 7 +L 3 +U 15 +L 5 +R 9 +L 12 +U 1 +L 16 +D 4 +L 5 +U 16 +R 6 +D 4 +U 6 +R 3 +L 1 +D 7 +L 4 +D 1 +U 5 +D 1 +L 6 +R 2 +L 8 +R 3 +L 12 +D 15 +R 9 +L 5 +U 12 +L 5 +U 9 +R 14 +D 16 +R 13 +L 12 +U 3 +L 16 +D 3 +R 6 +U 2 +R 4 +D 2 +L 6 +D 15 +L 11 +D 6 +U 9 +D 13 +U 7 +L 10 +D 12 +L 4 +R 9 +U 5 +R 9 +U 16 +R 15 +D 10 +R 14 +L 8 +U 8 +D 8 +R 13 +U 6 +R 5 +D 9 +L 11 +R 1 +D 4 +L 3 +D 1 +U 11 +R 2 +L 7 +R 14 +D 5 +R 16 +U 11 +L 2 +D 1 +U 4 +R 15 +L 13 +R 3 +U 1 +R 1 +U 3 +R 16 +D 1 +L 4 +R 9 +L 3 +D 14 +R 15 +D 13 +U 13 +D 5 +U 8 +L 3 +U 6 +D 10 +U 6 +D 2 +U 13 +R 5 +L 16 +R 16 +U 12 +R 10 +D 13 +L 1 +D 13 +R 15 +D 7 +R 7 +U 16 +R 10 +U 7 +L 14 +D 4 +L 6 +U 9 +L 15 +R 6 +L 14 +D 5 +R 6 +D 5 +L 6 +R 1 +U 13 +L 15 +R 14 +L 12 +D 2 +L 1 +U 1 +R 13 +L 11 +R 15 +D 17 +L 13 +R 8 +D 14 +R 2 +D 1 +R 3 +U 8 +R 8 +L 14 +D 6 +U 3 +D 9 +R 12 +L 13 +U 2 +D 8 +U 15 +D 16 +L 5 +D 7 +U 15 +R 7 +L 5 +R 13 +D 4 +L 7 +R 1 +D 7 +L 11 +R 2 +U 17 +L 6 +U 15 +D 5 +R 17 +D 12 +U 17 +L 3 +R 15 +U 7 +L 2 +R 5 +D 17 +L 12 +U 10 +D 5 +L 16 +R 17 +D 2 +R 15 +D 4 +U 1 +D 5 +U 10 +L 8 +U 16 +D 2 +L 11 +R 7 +U 15 +L 15 +D 2 +L 8 +R 3 +U 8 +R 7 +U 6 +L 17 +U 8 +R 6 +L 13 +R 6 +D 13 +L 9 +U 2 +R 7 +D 14 +L 10 +U 8 +D 10 +U 4 +R 3 +L 1 +D 5 +U 18 +L 1 +U 9 +D 4 +R 3 +D 11 +R 9 +U 18 +D 12 +R 13 +L 8 +D 6 +U 13 +R 6 +U 15 +R 14 +U 11 +R 11 +D 15 +L 7 +R 11 +D 16 +U 14 +R 15 +D 16 +R 3 +D 10 +R 6 +U 17 +L 9 +R 1 +D 12 +R 18 +U 11 +L 2 +R 5 +L 10 +U 13 +L 3 +D 15 +U 14 +D 13 +R 5 +U 15 +L 9 +U 6 +D 16 +L 1 +U 1 +D 12 +R 18 +L 13 +R 10 +U 14 +L 13 +U 3 +L 2 +R 11 +U 18 +D 14 +R 4 +L 6 +R 10 +U 18 +L 18 +R 9 +L 11 +U 4 +D 5 +L 15 +R 13 +L 18 +U 16 +L 1 +R 12 +U 17 +D 11 +U 1 +L 13 +U 7 +D 3 +U 5 +R 8 +D 4 +L 7 +D 17 +U 9 +R 1 +L 18 +U 13 +L 7 +U 12 +D 2 +R 18 +D 12 +U 11 +R 13 +U 12 +L 13 +R 7 +U 6 +D 5 +L 13 +D 15 +R 12 +D 8 +L 19 +U 10 +L 4 +D 18 +U 9 +D 5 +U 2 +L 1 +D 2 +R 8 +U 9 +R 1 +D 11 +U 18 +R 11 +D 19 +U 6 +D 14 +U 6 +D 4 +U 2 +L 12 +D 15 +L 10 +R 5 +U 16 +L 3 +D 8 +L 10 +D 7 +R 16 +D 8 +R 6 +L 16 +R 6 +D 8 +U 15 +D 1 +L 14 +U 14 +R 16 +L 14 +D 2 +R 6 +D 5 +R 14 +L 15 +D 2 +R 15 +L 4 +U 18 +R 8 +D 6 +R 7 +L 2 +U 5 +L 19 +R 17 +L 19 +R 13 +L 2 +U 7 +D 19 +R 9 +L 8 +D 18 +U 2 +R 3 +U 7 +D 9 +R 12 +U 13 +L 15 +U 2 +D 6 +R 18 +D 7 +L 10 +R 4 +L 12 +D 6 +L 4 +D 10 +L 7 +U 12 +L 9 +R 12 +L 13 +R 13 +L 18 +R 18 +U 7 +D 5 +R 8 +D 18 +L 11 +D 5 +L 1 +U 6 +R 19 +U 17 +R 16 +L 8 +R 11 +U 17 +D 1 +R 11 +L 12 +D 4 +U 13 diff --git a/src/Days/D09.hs b/src/Days/D09.hs new file mode 100644 index 0000000..bc0c626 --- /dev/null +++ b/src/Days/D09.hs @@ -0,0 +1,110 @@ +{-# LANGUAGE ImportQualifiedPost #-} +{-# LANGUAGE LambdaCase #-} +{-# LANGUAGE RecordWildCards #-} +{-# OPTIONS_GHC -Wno-incomplete-patterns #-} + +module Days.D09 where + +import Common +import Data.Functor ((<&>)) + +import Control.Monad (foldM_) +import Control.Monad.ST (runST) +import Data.HashTable.ST.Basic qualified as HT +import Data.Hashable (Hashable (..)) +import Data.List (mapAccumL) +import Data.Set qualified as Set +import Data.Tuple (swap) +import Data.Tuple.Extra (dupe) +import Parse +import Text.Megaparsec (oneOf) +import Text.Megaparsec.Char (space) + +data Direction = U | D | L | R deriving (Read, Eq) +data Move = Move {direction :: Direction, distance :: Int} +type Intermediate = [Move] +data V2 = V2 !Int !Int deriving (Eq, Ord) +type Rope = [V2] + +instance Num V2 where + (+) (V2 a b) (V2 c d) = V2 (a + c) (b + d) + (*) = undefined + abs (V2 a b) = V2 (abs a) (abs b) + signum (V2 a b) = V2 (signum a) (signum b) + fromInteger = undefined + negate (V2 a b) = V2 (negate a) (negate b) + +instance Hashable V2 where + hashWithSalt salt (V2 x y) = 999119999 * x + y + salt + +parser :: Parser Intermediate +parser = someLines move + where + move = Move <$> direction <* space <*> number + + direction :: Parser Direction + direction = + oneOf "UDLR" <&> \case + 'U' -> U + 'D' -> D + 'L' -> L + 'R' -> R + +unit :: Direction -> V2 +unit R = V2 1 0 +unit L = V2 (-1) 0 +unit U = V2 0 1 +unit D = V2 0 (-1) + +dist :: V2 -> V2 -> Int +dist x y = + let V2 x' y' = abs (x - y) + in max x' y' + +type State = (V2, V2) + +step :: State -> Direction -> State +step (h, t) direction = + let newHead = h + unit direction + in (newHead, if doMove newHead t then h else t) + where + doMove :: V2 -> V2 -> Bool + doMove a b = + let (V2 x y) = abs (b - a) + in x > 1 || y > 1 + +trace :: Move -> [V2] +trace (Move{..}) = replicate distance (unit direction) + +headTrace :: [Move] -> [V2] +headTrace = tail . scanl (+) (V2 0 0) . concatMap trace + +moveRope :: V2 -> Rope -> (V2, Rope) +moveRope = mapAccumL go + where + go :: V2 -> V2 -> (V2, V2) + go prev next = + let newNext = follow prev next + in dupe newNext + + follow prev next = + let d = dist prev next + in if d < 2 then next else next + signum (prev - next) + +initial :: Int -> Rope +initial len = replicate len (V2 0 0) + +uniquesHint :: (Hashable a) => Int -> [a] -> Int +uniquesHint hint items = runST $ do + m <- HT.newSized hint + foldM_ (\_ item -> HT.insert m item ()) () items + HT.size m + +simulate :: Int -> [Move] -> Int +simulate n = Set.size . Set.fromList . tailTrace + where + tailTrace :: [Move] -> [V2] + tailTrace = snd . mapAccumL ((swap .) . flip moveRope) (initial n) . headTrace + +day :: Day +day = parsecDay parser (definitive . simulate 2, definitive . simulate 9) diff --git a/src/Lib.hs b/src/Lib.hs index 9ebaed2..24a379a 100644 --- a/src/Lib.hs +++ b/src/Lib.hs @@ -19,6 +19,7 @@ import Days.D05 qualified as D05 import Days.D06 qualified as D06 import Days.D07 qualified as D07 import Days.D08 qualified as D08 +import Days.D09 qualified as D09 import Data.ByteString.Char8 qualified as BS import Data.Text.IO qualified as T @@ -39,4 +40,5 @@ days = , [D06.day] , [D07.day] , [D08.day] + , [D09.day] ]