Python实现21点游戏重玩功能:如何复用已跳出的循环?
给Python版21点游戏添加重玩功能的方案
先修正原代码的小问题
你原代码里有个语法错误:playerIn == False 是比较运算符,应该改成赋值 playerIn = False,否则玩家选择“stay”后不会退出自己的回合。
核心修改思路
要实现重玩,就得把单局游戏的全部流程(包括初始化牌堆、发牌、游戏循环、胜负结算)放到一个外层循环里,每局结束后询问玩家是否继续,以此控制外层循环的启停。同时要注意,每局开始前必须重置所有游戏变量(牌堆、手牌、玩家/庄家状态),否则会因为上一局的残留数据导致逻辑混乱。
修改后的完整代码
import random name = input("请输入你的名字: ") # 定义生成完整牌堆的函数,方便每局重置 def create_deck(): return [2, 3, 4, 5, 6, 7, 8, 9, 10, 2, 3, 4, 5, 6, 7, 8, 9, 10, 2, 3, 4, 5, 6, 7, 8, 9, 10, 2, 3, 4, 5, 6, 7, 8, 9, 10, 'J', 'Q', 'K', 'A', 'J', 'Q', 'K', 'A', 'J', 'Q', 'K', 'A', 'J', 'Q', 'K', 'A'] # 发牌函数 def dealCard(turn, deck): card = random.choice(deck) turn.append(card) deck.remove(card) # 计算手牌总值 def total(turn): total = 0 face = ['J', 'K', 'Q'] for card in turn: if isinstance(card, int) and 1 <= card <= 10: total += card elif card in face: total += 10 else: total += 1 if total > 11 else 11 return total # 显示庄家手牌(隐藏第二张) def revealDealerHand(dealerHand): if len(dealerHand) == 2: return dealerHand[0] elif len(dealerHand) > 2: return dealerHand[0], dealerHand[1] # 重玩控制外层循环 play_again = True while play_again: # 每局初始化游戏变量 playerIn = True dealerIn = True deck = create_deck() playerHand = [] dealerHand = [] # 初始发牌 for _ in range(2): dealCard(dealerHand, deck) dealCard(playerHand, deck) # 核心游戏循环(你之前高亮的部分) while playerIn or dealerIn: print(f"\n庄家手牌: {revealDealerHand(dealerHand)} 和 X") print(f"\n你的手牌: {playerHand},总值: {total(playerHand)}") if playerIn: stayOrHit = input("\n要停牌还是要牌?(输入1停牌,2要牌): ") # 庄家逻辑:大于16则停牌 if total(dealerHand) > 16: dealerIn = False else: dealCard(dealerHand, deck) # 玩家逻辑 if playerIn: if stayOrHit == "1": playerIn = False else: dealCard(playerHand, deck) # 结束循环条件:玩家或庄家爆牌/ blackjack if total(playerHand) >= 21 or total(dealerHand) >= 21: break # 胜负结算 print(f"\n你的手牌: {playerHand},总值: {total(playerHand)}") print(f"庄家手牌: {dealerHand},总值: {total(dealerHand)}") if total(playerHand) == 21: print(f"BLACKJACK!牛啊 {name}!") elif total(dealerHand) == 21: print("BLACKJACK,庄家赢了,你输了!") elif total(playerHand) > 21: print("你爆牌了,庄家赢了!") elif total(dealerHand) > 21: print(f"庄家爆牌了,你赢了 {name}!") elif 21 - total(dealerHand) < 21 - total(playerHand): print("庄家赢了!") else: print(f"你赢了 {name}!") # 询问是否重玩 choice = input("\n要不要再玩一局?(输入y继续,其他退出): ").lower() play_again = choice == 'y'
关键改动说明
- 新增外层重玩循环:用
while play_again:包裹整个单局流程,玩家每局结束后选择是否继续。 - 重置游戏变量:每局开始前重新生成完整牌堆、清空手牌、重置
playerIn和dealerIn状态,避免上一局数据干扰。 - 修复赋值错误:把
playerIn == False改成playerIn = False,确保玩家选择停牌后能退出自己的回合。 - 优化牌堆管理:新增
create_deck()函数,每次重玩都生成全新的完整牌堆,解决原代码中牌堆逐渐耗尽的问题。 - 调整函数参数:给
dealCard和revealDealerHand传入对应参数,让函数更独立,避免依赖全局变量的副作用。
内容的提问来源于stack exchange,提问作者Ivanoo
相关产品推荐
相关产品推荐

