Jens Kadenbach 2 år sedan
förälder
incheckning
71972e30ec
8 ändrade filer med 2697 tillägg och 2 borttagningar
  1. 3
    0
      aoc2022.cabal
  2. 2500
    0
      ressources/day02-input
  3. 16
    0
      src/Day2.hs
  4. 31
    0
      src/Day2/Part1.hs
  5. 42
    0
      src/Day2/Part2.hs
  6. 58
    0
      src/Day2/Shared.hs
  7. 2
    2
      src/Lib.hs
  8. 45
    0
      test/Day2Spec.hs

+ 3
- 0
aoc2022.cabal Visa fil

@@ -28,6 +28,9 @@ library
28 28
       Day1
29 29
       Day1.Internal
30 30
       Day2
31
+      Day2.Part1
32
+      Day2.Part2
33
+      Day2.Shared
31 34
       Lib
32 35
   other-modules:
33 36
       Paths_aoc2022

+ 2500
- 0
ressources/day02-input
Filskillnaden har hållits tillbaka eftersom den är för stor
Visa fil


+ 16
- 0
src/Day2.hs Visa fil

@@ -0,0 +1,16 @@
1
+module Day2 (
2
+  day2
3
+) where
4
+
5
+import Day2.Part1
6
+import Day2.Part2
7
+
8
+day2 :: IO ()
9
+day2 = do
10
+   input <- readFile "ressources/day02-input"
11
+   putStrLn "Day1"
12
+   let score1 = day2_1 input
13
+   putStrLn ("Score of all games: " ++ show score1)
14
+   let score2 = day2_2 input
15
+   putStrLn ("Score of all games according to plan: " ++ show score2)
16
+   return ()

+ 31
- 0
src/Day2/Part1.hs Visa fil

@@ -0,0 +1,31 @@
1
+module Day2.Part1 (
2
+parseGameList,
3
+readGame,
4
+playGames,
5
+day2_1
6
+) where
7
+
8
+import Day2.Shared
9
+
10
+parseGameList :: String -> [Game]
11
+parseGameList = map readGame . lines
12
+
13
+readGame :: String -> Game
14
+readGame [x, ' ', y] = Game (opponent x, me y)
15
+  where
16
+    opponent 'A' = Rock
17
+    opponent 'B' = Paper
18
+    opponent 'C' = Scissors
19
+    opponent _ = error $ "unknown opponent shape: " ++ [x]
20
+    me 'X' = Rock
21
+    me 'Y' = Paper
22
+    me 'Z' = Scissors
23
+    me _ = error $ "unknown me shape: " ++ [x]
24
+readGame xs = error $ "readGame not implemented for " ++ xs
25
+
26
+playGames :: [Game] -> Score
27
+playGames = foldMap play
28
+
29
+day2_1 :: String -> Score
30
+day2_1 = playGames . parseGameList
31
+

+ 42
- 0
src/Day2/Part2.hs Visa fil

@@ -0,0 +1,42 @@
1
+module Day2.Part2 (
2
+day2_2,
3
+readGameHints,
4
+GameHint (GameHint),
5
+Outcome (Win, Draw, Lose),
6
+executePlan
7
+) where
8
+
9
+import Day2.Shared
10
+
11
+data Outcome = Win | Draw | Lose deriving (Show, Eq)
12
+
13
+newtype GameHint = GameHint (Shape, Outcome) deriving (Show, Eq)
14
+
15
+readGameHints :: String -> [GameHint]
16
+readGameHints = map parseGameHint . lines
17
+
18
+parseGameHint :: String -> GameHint
19
+parseGameHint [x, ' ', y] = GameHint (opponent x, me y)
20
+  where
21
+    opponent 'A' = Rock
22
+    opponent 'B' = Paper
23
+    opponent 'C' = Scissors
24
+    opponent _ = error $ "unknown shape: " ++ [x]
25
+    me 'X' = Lose
26
+    me 'Y' = Draw
27
+    me 'Z' = Win
28
+    me _ = error $ "unknown game result: " ++ [x]
29
+parseGameHint xs = error $ "readGameHint not implemented for " ++ xs
30
+
31
+playGames :: [GameHint] -> Score
32
+playGames = foldMap (play . executePlan)
33
+
34
+executePlan :: GameHint -> Game
35
+executePlan (GameHint (x, Draw)) = Game (x, x)
36
+executePlan (GameHint (x, Win)) = Game (x, winAgainst x)
37
+executePlan (GameHint (x, Lose)) = Game (x, loseAgainst x)
38
+
39
+
40
+day2_2 :: String -> Score
41
+day2_2 = playGames . readGameHints
42
+

+ 58
- 0
src/Day2/Shared.hs Visa fil

@@ -0,0 +1,58 @@
1
+module Day2.Shared (
2
+  Shape (Rock, Paper, Scissors),
3
+  shapeScore,
4
+  Score (Score),
5
+  Game (Game),
6
+  gameWin,
7
+  gameLoss,
8
+  gameDraw,
9
+  play,
10
+  winAgainst,
11
+  loseAgainst
12
+) where
13
+
14
+data Shape = Rock | Paper | Scissors
15
+  deriving (Show, Eq)
16
+
17
+newtype Score = Score Int
18
+  deriving (Show, Eq)
19
+
20
+instance Semigroup Score where
21
+  (<>) (Score x) (Score y) = Score (x + y)
22
+
23
+instance Monoid Score where
24
+  mempty = Score 0
25
+
26
+gameWin :: Score
27
+gameWin = Score 6
28
+
29
+gameDraw :: Score
30
+gameDraw = Score 3
31
+
32
+gameLoss :: Score
33
+gameLoss = Score 0
34
+
35
+newtype Game = Game (Shape, Shape)
36
+  deriving (Show, Eq)
37
+
38
+shapeScore :: Shape -> Score
39
+shapeScore Rock = Score 1
40
+shapeScore Paper = Score 2
41
+shapeScore Scissors = Score 3
42
+
43
+winAgainst :: Shape -> Shape
44
+winAgainst Rock = Paper
45
+winAgainst Paper = Scissors
46
+winAgainst Scissors = Rock
47
+
48
+loseAgainst :: Shape -> Shape
49
+loseAgainst Rock = Scissors
50
+loseAgainst Paper = Rock
51
+loseAgainst Scissors = Paper
52
+
53
+
54
+play :: Game -> Score
55
+play (Game (x, y))
56
+ | winAgainst  x == y = gameWin  <> shapeScore y
57
+ | loseAgainst x == y = gameLoss <> shapeScore y
58
+ | otherwise          = gameDraw <> shapeScore y

+ 2
- 2
src/Lib.hs Visa fil

@@ -2,8 +2,8 @@ module Lib
2 2
     ( someFunc
3 3
     ) where
4 4
       
5
-import Day1      
5
+import Day2      
6 6
 
7 7
 someFunc :: IO ()
8
-someFunc = day1
8
+someFunc = day2
9 9
 

+ 45
- 0
test/Day2Spec.hs Visa fil

@@ -0,0 +1,45 @@
1
+{-# LANGUAGE OverloadedStrings #-}
2
+module Day2Spec (spec) where
3
+import Test.Hspec
4
+import Day2.Shared
5
+import Day2.Part1
6
+import Day2.Part2
7
+
8
+input :: String 
9
+input = "A Y\nB X\nC Z"
10
+
11
+spec :: Spec
12
+spec =
13
+  describe "Day2" $ do
14
+    describe "Day2 - Shared" $ do
15
+      it "should have scores for shapes" $ do
16
+        shapeScore Rock `shouldBe` Score 1
17
+        shapeScore Paper `shouldBe` Score 2
18
+        shapeScore Scissors `shouldBe` Score 3
19
+      it "can sum up scores" $ do
20
+        Score 1 <> Score 2 `shouldBe` Score 3
21
+      it "can play games" $ do
22
+        play (Game (Rock, Paper)) `shouldBe` shapeScore Paper <> gameWin
23
+    describe "Day2 - Part1" $ do
24
+      it "can parse game plan" $ do
25
+         parseGameList input `shouldBe` games
26
+      it "can parse a single game" $ do
27
+        readGame "A Y" `shouldBe` Game (Rock, Paper)
28
+        readGame "B X" `shouldBe` Game (Paper, Rock)
29
+        readGame "C Z" `shouldBe` Game (Scissors, Scissors)
30
+      it "can sum up games" $ do
31
+        playGames games `shouldBe` Score 15
32
+      it "can play game plan" $ do
33
+         day2_1 input `shouldBe` Score 15
34
+    describe "Day2 - Part1" $ do
35
+      it "can parse game plan as hints" $ do
36
+         readGameHints input `shouldBe` gameHints
37
+      it "can convert game plan" $ do
38
+         map executePlan gameHints `shouldBe` [Game (Rock, Rock),
39
+          Game (Paper, Rock), Game (Scissors, Rock)]
40
+      it "can play a game plan" $ do
41
+         day2_2 input `shouldBe` Score 12
42
+      where
43
+        games = [Game (Rock, Paper), Game (Paper, Rock), Game (Scissors, Scissors)]
44
+        gameHints = [GameHint (Rock, Draw), GameHint (Paper, Lose), GameHint (Scissors, Win)]
45
+

Laddar…
Avbryt
Spara