From 8a966890d5b9bc7d7f4ec8734c21b01ce5a41159 Mon Sep 17 00:00:00 2001 From: wangsiyuan <2392948297@qq.com> Date: Sun, 1 Dec 2024 00:34:47 +0800 Subject: [PATCH] 1 1 --- src/engine/meld.py | 37 ++++++++++++++++++++++++++++++ test.py | 38 ++++++++++++++++++++++++++++--- tests/test_game_status.py | 47 ++++++++++++++++++++++++++++++++++----- 3 files changed, 114 insertions(+), 8 deletions(-) create mode 100644 src/engine/meld.py diff --git a/src/engine/meld.py b/src/engine/meld.py new file mode 100644 index 0000000..8d388be --- /dev/null +++ b/src/engine/meld.py @@ -0,0 +1,37 @@ +from src.engine.mahjong_tile import MahjongTile + +class Meld: + def __init__(self, tile, type: str): + """ + 初始化一个碰或杠的对象。 + + :param tile: MahjongTile 对象,表示碰或杠的牌。 + :param type: 字符串,'碰' 或 '杠',表示碰或杠。 + """ + if not isinstance(tile, MahjongTile): + raise TypeError("tile 必须是 MahjongTile 类型") + if type not in ['碰', '杠']: + raise ValueError("type 必须是 '碰' 或 '杠'") + + self.tile = tile + self.type = type + self.count = 3 if type == '碰' else 4 # 碰为3张,杠为4张 + + def __repr__(self): + return f"({self.type}: {self.tile} x{self.count})" + + def __eq__(self, other): + if not isinstance(other, Meld): + return False + return self.tile == other.tile and self.type == other.type + + def __hash__(self): + return hash((self.tile, self.type)) + + def is_triplet(self): + """是否为碰""" + return self.type == '碰' + + def is_kong(self): + """是否为杠""" + return self.type == '杠' \ No newline at end of file diff --git a/test.py b/test.py index 81e1c88..952f56e 100644 --- a/test.py +++ b/test.py @@ -1,3 +1,35 @@ -import torch -print(torch.cuda.is_available()) # 如果返回True,说明可以使用GPU -print(torch.__version__) \ No newline at end of file +from src.engine.chengdu_mahjong_state import ChengduMahjongState +from src.engine.hand import Hand + +from src.engine.mahjong_tile import MahjongTile + +hand = Hand() + +# 添加暗牌 +hand.add_tile(MahjongTile("筒", 6)) +hand.add_tile(MahjongTile("筒", 6)) +hand.add_tile(MahjongTile("筒", 6)) +hand.add_tile(MahjongTile("筒", 7)) +hand.add_tile(MahjongTile("筒", 7)) +hand.add_tile(MahjongTile("筒", 7)) +hand.add_tile(MahjongTile("筒", 8)) +hand.add_tile(MahjongTile("筒", 8)) +hand.add_tile(MahjongTile("筒", 8)) +# 添加对子 +hand.add_tile(MahjongTile("筒", 2)) +hand.add_tile(MahjongTile("筒", 2)) + +# 初始化游戏状态 +state = ChengduMahjongState() +state.hands[0] = hand + +# 设置明牌(杠) +melds_list = [ + ("杠", MahjongTile("筒", 9)), # 表示明杠了4张9筒 +] +state.melds[0] = melds_list + +# 设置缺门为 "万" +missing_suit = "万" +print(f"\n当前手牌: {state.hands[0]}, 明牌: {state.melds[0]}") +state.can_win(state.hands[0], state.melds[0], missing_suit) \ No newline at end of file diff --git a/tests/test_game_status.py b/tests/test_game_status.py index fdb0ba7..6da9b4a 100644 --- a/tests/test_game_status.py +++ b/tests/test_game_status.py @@ -41,6 +41,7 @@ def test_can_win_with_pure_sequences(): hand.add_tile(MahjongTile("万", 5)) state = ChengduMahjongState() + state.melds[0] = [] state.hands[0] = hand # 设置缺门为 "条",因为手牌中没有 "条" @@ -48,7 +49,7 @@ def test_can_win_with_pure_sequences(): print(f"\n,state.hand[0]: {state.hands[0]}") # 调用 can_win 方法并断言胡牌 - assert state.can_win(state.hands[0], missing_suit) == True, "测试失败:纯顺子应该可以胡牌" + assert state.can_win(state.hands[0], state.melds[0],missing_suit) == True, "测试失败:纯顺子应该可以胡牌" def test_can_win_with_sequence_and_triplet(): @@ -72,13 +73,14 @@ def test_can_win_with_sequence_and_triplet(): state = ChengduMahjongState() state.hands[0] = hand + state.melds[0] = [] # 设置缺门为 "条",因为手牌中没有 "条" missing_suit = "条" print(f"\n,state.hand[0]: {state.hands[0]}") # 调用 can_win 方法并断言胡牌 - assert state.can_win(state.hands[0], missing_suit) == True, "测试失败:顺子 + 刻子应该可以胡牌" + assert state.can_win(state.hands[0], state.melds[0],missing_suit) == True, "测试失败:顺子 + 刻子应该可以胡牌" def test_can_win_with_triplets_and_pair(): """测试刻子和对子胡牌""" @@ -100,13 +102,13 @@ def test_can_win_with_triplets_and_pair(): state = ChengduMahjongState() state.hands[0] = hand - + state.melds[0] = [] # 设置缺门为 "万",因为手牌中没有 "万" missing_suit = "万" print(f"\n,state.hand[0]: {state.hands[0]}") # 调用 can_win 方法并断言胡牌 - assert state.can_win(state.hands[0], missing_suit) == True, "测试失败:刻子和对子应该可以胡牌" + assert state.can_win(state.hands[0], state.melds[0],missing_suit) == True, "测试失败:刻子和对子应该可以胡牌" def test_can_win_with_pure_one_suit(): @@ -130,12 +132,47 @@ def test_can_win_with_pure_one_suit(): state = ChengduMahjongState() state.hands[0] = hand + state.melds[0] = [] # 设置缺门为 "万",因为手牌中只有 "筒" missing_suit = "万" print(f"\n,state.hand[0]: {state.hands[0]}") # 调用 can_win 方法并断言胡牌 - assert state.can_win(state.hands[0], missing_suit) == True, "测试失败:清一色不带杠应该可以胡牌" + assert state.can_win(state.hands[0], state.melds[0],missing_suit) == True, "测试失败:清一色不带杠应该可以胡牌" +def test_can_win_with_pure_one_suit_and_gang(): + """测试带杠的清一色胡牌""" + hand = Hand() + + # 添加暗牌 + hand.add_tile(MahjongTile("筒", 6)) + hand.add_tile(MahjongTile("筒", 6)) + hand.add_tile(MahjongTile("筒", 6)) + hand.add_tile(MahjongTile("筒", 7)) + hand.add_tile(MahjongTile("筒", 7)) + hand.add_tile(MahjongTile("筒", 7)) + hand.add_tile(MahjongTile("筒", 8)) + hand.add_tile(MahjongTile("筒", 8)) + hand.add_tile(MahjongTile("筒", 8)) + # 添加对子 + hand.add_tile(MahjongTile("筒", 2)) + hand.add_tile(MahjongTile("筒", 2)) + + # 初始化游戏状态 + state = ChengduMahjongState() + state.hands[0] = hand + + # 设置明牌(杠) + melds_list = [ + ("杠", MahjongTile("筒", 9)) + ] + state.melds[0] = melds_list + + # 设置缺门为 "万" + missing_suit = "万" + print(f"\n当前手牌: {state.hands[0]}, 明牌: {state.melds[0]}") + + # 调用 can_win 方法并断言胡牌 + assert state.can_win(state.hands[0], state.melds[0], missing_suit) == True, "测试失败:带杠的清一色应该可以胡牌" \ No newline at end of file