You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

扑克程序高牌比较功能异常求助

Python扑克程序高牌比较功能故障排查求助

开发Python扑克程序时,采用花色符号替代字母表示花色,目前仅高牌比较功能异常:当所有玩家手牌均为高牌时,即便自身手牌牌力最低,系统仍判定自己得分。设计思路为:若多名玩家最大牌相同,则复制各玩家手牌列表,移除已比较的相同牌,逐步淘汰牌力较低的玩家直至决出胜者;若两名玩家手牌完全一致则判定平局,但该逻辑未正常运行,其余牌型判定功能均正常。

问题代码

import random, time, json
from random import shuffle
from collections import Counter
from enum import Enum

class CardSuits(Enum):
    Hearts = "Hearts"
    Diamonds = "Diamonds"
    Clubs = "Clubs"
    Spades = "Spades"

class CardValues(Enum):
    Two = 2
    Three = 3
    Four = 4
    Five = 5
    Six = 6
    Seven = 7
    Eight = 8
    Nine = 9
    Ten = 10
    Jack = 11
    Queen = 12
    King = 13
    Ace = 14


class Card:

    _symbols = {"Hearts": "♥️", "Diamonds": "♦️", "Clubs": "♣️", "Spades": "♠"}

    _numbers = {2: "2",
                3: "3",
                4: "4",
                5: "5",
                6: "6",
                7: "7",
                8: "8",
                9: "9",
                10: "10",
                11: "J",
                12: "Q",
                13: "K",
                14: "A"}
    
    def __init__(self, suit: CardSuits, value: CardValues) -> None:
        self.suit = suit
        self.value = value

    def __str__(self) -> str:
        return f"{self._numbers[self.value.value]}{self._symbols[self.suit.name]}"

    def __repr__(self) -> str:
        return f"{self._numbers[self.value.value]}{self._symbols[self.suit.name]}"

#GAME START
def start():
    play = input("You wanna play? ")
    if play.lower() in ("yes", "sure", "yeah"):
        all_cards = [Card(suits, value) for suits in CardSuits for value in CardValues]
        shuffle(all_cards)
        unique_cards = set()
        while len(unique_cards) < 5:
            unique_cards.add(random.choice(all_cards))
        cards = list(unique_cards)
        print("Your cards are:", ", ".join(str(card) for card in cards))
        time.sleep(4)

    #OPPONENTS CARD CREATION
    # First opponent
    unique_cards = set()
    while len(unique_cards) < 5:
        unique_cards.add(random.choice(all_cards))
    first_opponent_cards = list(unique_cards)
    # Second
    unique_cards = set()
    while len(unique_cards) < 5:
        unique_cards.add(random.choice(all_cards))
        second_opponent_cards = list(unique_cards)
    #CHECKING PHASE
    def checking_phase(cards):
        High_Card, Pair, Two_Pair, Three_of_a_Kind, Straight, Flush, Full, Four_of_a_Kind, Straight_Flush, Royal_Flush = ("High Card", "Pair", "Two Pair", "Three of a Kind", "Straight", "Flush", "Full", "Four of a Kind", "Straight Flush", "Royal Flush")
        if is_royal_flush:
            return Royal_Flush
        #elif series for returning other combinations
        else:
            return High_Card

    user_hand = checking_phase(cards)
    first_opponent_hand = checking_phase(first_opponent_cards)
    second_opponent_hand = checking_phase(second_opponent_cards)
    
    #SCORE DASHBOARD
    players = [user_hand, first_opponent_hand, second_opponent_hand]
    scores = [0, 0, 0] if not scores else scores
    # Determina il giocatore con la combinazione più alta
    max_hand_index = max(range(len(players)), key=lambda i: players[i])
    # Incrementa il punteggio del giocatore con la combinazione più alta
    if user_hand == "High Card" and first_opponent_hand == "High Card" and second_opponent_hand == "High Card":
        cards_remove_cycle = 0
        user_high = max(card.value.value for card in cards)
        first_op_high = max(card.value.value for card in first_opponent_cards)
        second_op_high = max(card.value.value for card in second_opponent_cards)
        high_list = [user_high, first_op_high, second_op_high]
        #caso in cui ci siano due o più player con max identici
        if user_high == first_op_high or user_high == second_op_high or first_op_high == second_op_high:
            print("Eureka! it works")
            comparing_HC_cycle = 0
            for player in players:
                for card in cards:
                    user_copyli = cards[:]
                    first_copyli = first_opponent_cards[:]
                    second_copyli = second_opponent_cards[:]
                    high_copyli = [user_copyli, first_copyli, second_copyli]
                    # max_HC_value = max(high_copyli)
                    max_HC_value = max(max(card.value.value for card in hand) for hand in high_copyli)
                    # Filtra la lista high_copyli per rimuovere i giocatori senza la carta più alta
                    high_copyli = [hand for hand in high_copyli if max(card.value.value for card in hand) == max_HC_value]
                    
                    if user_high in user_copyli:
                        user_copyli.remove(user_high)
                    if first_op_high in first_copyli:
                        first_copyli.remove(first_op_high)
                    if second_op_high in second_copyli:
                        second_copyli.remove(second_op_high)

                    user_high = max(card.value.value for card in cards)
                    first_op_high = max(card.value.value for card in first_opponent_cards)
                    second_op_high = max(card.value.value for card in second_opponent_cards)
                    
                    comparing_HC_cycle += 1
                    if comparing_HC_cycle > 4:
                        winner_index = players.index(player)
                        scores[winner_index] += 1
                        print("arriva, ma non funzia")
                        break

            else: #caso in cui il max di ogni player sia diverso, quindi solo 1 vincitore
                high_card_winner = max(high_list)
                HC_winner_index = high_list.index(high_card_winner)
                scores[HC_winner_index] += 1                                      
        else:
            scores[max_hand_index] += 1
        winning_player = ["You", "First opponent", "Second opponent"]
        if winning_player[max_hand_index] == "You":
            print("You won!")
        else:
            print(f"{winning_player[max_hand_index]} won. May you'll be luckier next time")

        score_phrase = """
        SCORE:          User: {}   |   First opponent: {}   |   Second opponent: {}   """
        print(score_phrase.format(scores[0], scores[1], scores[2]))

关键问题分析

  1. 循环逻辑完全错误:嵌套的for player in players和for card in cards毫无意义,且每次循环都重新复制原始手牌,没有保留之前移除牌的状态,等于始终在比较原始手牌的最大牌,根本没实现“逐步移除已比较牌”的逻辑。
  2. 对象与数值判断混淆:user_high是牌的数值(如14),而user_copyli里是Card对象,user_high in user_copyli永远为False,导致移除操作从未执行。
  3. 牌值更新错误:更新user_high时使用的是原始cards列表,而非复制后已移除牌的user_copyli,导致每次都取原始手牌的最大牌,比较流程无法推进。
  4. 胜者判定逻辑错误:winner_index = players.index(player)中的player是字符串"High Card",所有玩家的手牌类型都是这个值,因此index()永远返回0(用户的索引),这就是系统总是判定用户赢的核心原因。
  5. 其他小问题:
    • 第二个对手的手牌生成逻辑错误:second_opponent_cards = list(unique_cards)放在while循环内部,会导致每次添加一张牌就重新赋值,应移到循环外部。
    • scores初始化错误:scores = [0,0,0] if not scores else scores中scores首次运行时未定义,会触发NameError,应直接初始化scores = [0, 0, 0]。
    • checking_phase函数中is_royal_flush未定义,需补充完整牌型判定逻辑。

修复方案

1. 实现正确的高牌比较函数

将每个玩家的手牌转换为降序排列的数值列表,逐位比较牌力,直到决出唯一胜者或判定平局:

def compare_high_cards(players_hands):
    # 转换为降序排列的数值列表
    sorted_value_lists = []
    for hand in players_hands:
        values = sorted([card.value.value for card in hand], reverse=True)
        sorted_value_lists.append(values)
    
    # 从最大牌开始逐位比较
    for position in range(5):
        current_values = [vals[position] for vals in sorted_value_lists]
        max_current_val = max(current_values)
        # 筛选出当前位持有最大值的玩家索引
        remaining_indices = [idx for idx, val in enumerate(current_values) if val == max_current_val]
        if len(remaining_indices) == 1:
            return remaining_indices[0]  # 返回唯一胜者索引
    
    return -1  # 所有牌值相同,平局

2. 替换原高牌比较逻辑

在主函数中调用上述函数,替换原错误的高牌比较代码:

if user_hand == "High Card" and first_opponent_hand == "High Card" and second_opponent_hand == "High Card":
    players_hands = [cards, first_opponent_cards, second_opponent_cards]
    winner_idx = compare_high_cards(players_hands)
    
    if winner_idx == -1:
        print("平局!")
    else:
        scores[winner_idx] += 1
        winning_player = ["You", "First opponent", "Second opponent"]
        print(f"{winning_player[winner_idx]} won!")

3. 修复其他小问题

  • 第二个对手手牌生成修正:
# Second opponent
unique_cards = set()
while len(unique_cards) < 5:
    unique_cards.add(random.choice(all_cards))
second_opponent_cards = list(unique_cards)  # 移到循环外部
  • 初始化scores:
scores = [0, 0, 0]

内容的提问来源于stack exchange,提问作者Yes

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.26 05:02:03