diff --git a/tests/test_games/AM-driver-subgame.efg b/tests/test_games/AM-driver-subgame.efg new file mode 100644 index 000000000..3244fc8b0 --- /dev/null +++ b/tests/test_games/AM-driver-subgame.efg @@ -0,0 +1,10 @@ +EFG 2 R "Untitled Extensive Game" { "Player 1" "Player 2" } +"" + +p "" 1 1 "" { "1" "2" } 0 +p "" 1 1 "" { "1" "2" } 0 +t "" 1 "Outcome 1" { 1, -1 } +p "" 2 1 "" { "1" "2" } 0 +t "" 2 "Outcome 2" { 2, -2 } +t "" 3 "Outcome 3" { 3, -3 } +t "" 4 "Outcome 4" { 4, -4 } diff --git a/tests/test_games/subgames.efg b/tests/test_games/subgames.efg new file mode 100644 index 000000000..1e1d21278 --- /dev/null +++ b/tests/test_games/subgames.efg @@ -0,0 +1,40 @@ +EFG 2 R "Untitled Extensive Game" { "Player 1" "Player 2" } +"" + +p "" 2 1 "" { "1" "2" } 0 +p "" 1 1 "" { "1" "2" } 0 +t "" 1 "Outcome 1" { 1, -1 } +t "" 2 "Outcome 2" { 2, -2 } +p "" 1 2 "" { "1" "2" } 0 +p "" 2 2 "" { "1" "2" } 0 +t "" 3 "Outcome 3" { 3, -3 } +p "" 1 3 "" { "1" "2" } 0 +t "" 4 "Outcome 4" { 4, -4 } +t "" 5 "Outcome 5" { 5, -5 } +p "" 2 2 "" { "1" "2" } 0 +p "" 2 3 "" { "1" "2" } 0 +p "" 1 4 "" { "1" "2" } 0 +p "" 2 4 "" { "1" "2" } 0 +t "" 6 "Outcome 6" { 6, -6 } +t "" 7 "Outcome 7" { 7, -7 } +t "" 8 "Outcome 8" { 8, -8 } +p "" 1 5 "" { "1" "2" } 0 +p "" 2 6 "" { "1" "2" } 0 +t "" 9 "Outcome 9" { 9, -9 } +t "" 10 "Outcome 10" { 10, -10 } +p "" 2 6 "" { "1" "2" } 0 +p "" 1 7 "" { "1" "2" } 0 +p "" 2 5 "" { "1" "2" } 0 +p "" 1 4 "" { "1" "2" } 0 +t "" 11 "Outcome 11" { 11, -11 } +t "" 12 "Outcome 12" { 12, -12 } +p "" 1 4 "" { "1" "2" } 0 +t "" 13 "Outcome 13" { 13, -13 } +t "" 14 "Outcome 14" { 14, -14 } +t "" 15 "Outcome 15" { 15, -15 } +p "" 1 7 "" { "1" "2" } 0 +t "" 16 "Outcome 16" { 16, -16 } +t "" 17 "Outcome 17" { 17, -17 } +p "" 1 6 "" { "1" "2" } 0 +t "" 18 "Outcome 18" { 18, -18 } +t "" 19 "Outcome 19" { 19, -19 } diff --git a/tests/test_node.py b/tests/test_node.py index e11524522..0e063ed95 100644 --- a/tests/test_node.py +++ b/tests/test_node.py @@ -86,11 +86,30 @@ def test_is_successor_of(): game.root.is_successor_of(game.players[0]) -def test_is_subgame_root(): - """Test whether nodes are correctly labeled as roots of proper subgames.""" - game = games.read_from_file("basic_extensive_game.efg") - assert game.root.is_subgame_root - assert not game.root.children[0].is_subgame_root +@pytest.mark.parametrize("game, expected_result", [ + # Games without Absent-Mindedness for which the legacy method is known to be correct. + (games.read_from_file("wichardt.efg"), {0}), + (games.read_from_file("e02.efg"), {0, 2, 4}), + (games.read_from_file("subgames.efg"), {0, 1, 4, 7, 11, 13, 34}), + + pytest.param( + games.read_from_file("AM-driver-subgame.efg"), + {0, 3}, # The correct set of subgame roots + marks=pytest.mark.xfail( + reason="Current method does not detect roots of proper subgames " + "that are members of AM-infosets." + ) + ), +]) +def test_legacy_is_subgame_root_set(game: gbt.Game, expected_result: set): + """ + Tests the legacy `node.is_subgame_root` against an expected set of nodes. + Includes both passing cases and games with Absent-Mindedness where it is expected to fail. + """ + list_nodes = list(game.nodes) + expected_roots = {list_nodes[i] for i in expected_result} + legacy_roots = {node for node in game.nodes if node.is_subgame_root} + assert legacy_roots == expected_roots def test_append_move_error_player_actions():