diff --git a/2022/02/main.py b/2022/02/main.py
index b55a3ee..267bb73 100644
--- a/2022/02/main.py
+++ b/2022/02/main.py
@@ -1,4 +1,5 @@
 from enum import Enum
+from typing import Callable
 
 from utils.input import read_input_lines
 
@@ -21,7 +22,7 @@ class Outcome(Enum):
         self.points = points
 
 
-def play_game_from_line(line: str) -> int:
+def play_game_from_line(line: str, strategy: Callable[[Move, str], Move]) -> int:
     (opponent_char, response_char) = line.split(" ", maxsplit = 2)
     
     match opponent_char:
@@ -30,12 +31,7 @@ def play_game_from_line(line: str) -> int:
         case "C": opponent = Move.SCISSORS
         case _: raise ValueError(f"Invalid opponent move: {opponent_char}")
     
-    match response_char:
-        case "X": response = Move.ROCK
-        case "Y": response = Move.PAPER
-        case "Z": response = Move.SCISSORS
-        case _: raise ValueError(f"Invalid response move: {response_char}")
-    
+    response = strategy(opponent, response_char)
     outcome = play_game(response, opponent)
     return response.points + outcome.points
 
@@ -53,6 +49,40 @@ def play_game(me: Move, opponent: Move) -> Outcome:
         raise ValueError(f"Invalid move: {me}")
 
 
+# noinspection PyShadowingNames
+def play_games_from_all_lines(lines: list[str], strategy) -> int:
+    return sum(play_game_from_line(line, strategy) for line in lines)
+
+
+def strategy_response_char_determines_move(_: Move, response_char: str) -> Move:
+    match response_char:
+        case "X": return Move.ROCK
+        case "Y": return Move.PAPER
+        case "Z": return Move.SCISSORS
+        case _: raise ValueError(f"Invalid response move: {response_char}")
+
+
+def strategy_response_char_determines_outcome(opponent: Move, response_char: str) -> Move:
+    match response_char:
+        case "Y":  # Draw
+            return opponent
+        case "Z":  # Win
+            match opponent:
+                case Move.ROCK: return Move.PAPER
+                case Move.PAPER: return Move.SCISSORS
+                case Move.SCISSORS: return Move.ROCK
+        case "X":  # Lose
+            match opponent:
+                case Move.ROCK: return Move.SCISSORS
+                case Move.PAPER: return Move.ROCK
+                case Move.SCISSORS: return Move.PAPER
+        case _:
+            raise ValueError(f"Invalid response move: {response_char}")
+
+
 lines = read_input_lines()
-score = sum(play_game_from_line(line) for line in lines)
-print(f"Score: {score}")
+first_strategy_score = play_games_from_all_lines(lines, strategy_response_char_determines_move)
+second_strategy_score = play_games_from_all_lines(lines, strategy_response_char_determines_outcome)
+
+print(f"First strategy score: {first_strategy_score}")
+print(f"Second strategy score: {second_strategy_score}")