You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

Day5Spec.hs 3.3KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475
  1. {-# LANGUAGE QuasiQuotes #-}
  2. module Day5Spec (spec) where
  3. import Test.Hspec
  4. import Text.Heredoc
  5. import qualified Data.Sequence as S
  6. import Day5.Part1
  7. inputPart1 :: String
  8. inputPart1 = [str| [D]
  9. |[N] [C]
  10. |[Z] [M] [P]
  11. | 1 2 3
  12. |
  13. |move 1 from 2 to 1
  14. |move 3 from 1 to 3
  15. |move 2 from 2 to 1
  16. |move 1 from 1 to 2
  17. |]
  18. inputStacks :: String
  19. inputStacks = [str| [D]
  20. |[N] [C]
  21. |[Z] [M] [P]
  22. | 1 2 3
  23. |]
  24. inputOperations :: String
  25. inputOperations = [str|move 1 from 2 to 1
  26. |move 3 from 1 to 3
  27. |move 2 from 2 to 1
  28. |move 1 from 1 to 2
  29. |]
  30. spec :: Spec
  31. spec =
  32. describe "Day5" $ do
  33. describe "Part1" $ do
  34. it "parses Operations" $ do
  35. let operation = head . lines $ inputOperations
  36. parseOperation operation `shouldBe` Operation { count = 1, from = StackIndex 2, to = StackIndex 1 }
  37. it "parses stacks" $ do
  38. parseStacks (lines inputStacks) `shouldBe` S.fromList [Stack "NZ", Stack "DCM", Stack "P"]
  39. it "parses a single line of stacks" $ do
  40. let row = head . lines $ inputStacks
  41. parseRow row `shouldBe` S.fromList [Stack "", Stack "D"]
  42. it "combines stacks" $ do
  43. (Stack "AB" <> Stack "CD") `shouldBe` Stack "ABCD"
  44. it "combines rows" $ do
  45. S.fromList [Stack "", Stack "A"] `combineRows` S.fromList [Stack "B", Stack "B"] `shouldBe` S.fromList [Stack "B", Stack "AB"]
  46. S.empty `combineRows` S.fromList [Stack "B", Stack "B"] `shouldBe` S.fromList [Stack "B", Stack "B"]
  47. S.fromList [Stack "A", Stack "B"] `combineRows` S.empty `shouldBe` S.fromList [Stack "A", Stack "B"]
  48. S.singleton (Stack "") `combineRows` S.fromList[Stack "B", Stack "B"] `shouldBe` S.fromList [Stack "B", Stack "B"]
  49. S.fromList [Stack "A", Stack "B"] `combineRows` S.singleton (Stack "") `shouldBe` S.fromList [Stack "A", Stack "B"]
  50. it "splits input into stacks and operations" $ do
  51. parseInput inputPart1 `shouldBe`
  52. (S.fromList [Stack "NZ", Stack "DCM", Stack "P"],
  53. [ Operation { count = 1, from = StackIndex 2, to = StackIndex 1},
  54. Operation { count = 3, from = StackIndex 1, to = StackIndex 3},
  55. Operation { count = 2, from = StackIndex 2, to = StackIndex 1},
  56. Operation { count = 1, from = StackIndex 1, to = StackIndex 2}])
  57. it "exeutes a count=1 operation on a row" $ do
  58. let op = Operation { count = 1, from = StackIndex 2, to = StackIndex 3}
  59. let row = S.fromList [Stack "NZ", Stack "DCM", Stack "P"]
  60. executeOperation row op `shouldBe` S.fromList [Stack "NZ", Stack "CM", Stack "DP"]
  61. it "exeutes a count > 1 operation on a row" $ do
  62. let op = Operation { count = 2, from = StackIndex 2, to = StackIndex 3}
  63. let row = S.fromList [Stack "NZ", Stack "DCM", Stack "P"]
  64. executeOperation row op `shouldBe` S.fromList [Stack "NZ", Stack "M", Stack "CDP"]
  65. it "finds the top items on stacks" $ do
  66. let row = S.fromList [Stack "NZ", Stack "DCM", Stack "P"]
  67. findTopOfStacks row `shouldBe` S.fromList "NDP"
  68. it "solves the demo" $ do
  69. day5_1 inputPart1 `shouldBe` "CMZ"