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

Python双人文本回合制格斗游戏:修复生命值扣除TypeError报错

问题分析与修复方案

核心错误原因

触发TypeError: unsupported operand type(s) for -=: 'str' and 'str'的直接原因是这行完全错误的代码:

"defender_health"[0] -= "int";magnitude
  • "defender_health"是字符串字面量,不是可操作的变量,无法通过下标修改或执行减法运算
  • "int";magnitude是语法混乱的写法,分号在这里无意义,且试图用字符串和整数做运算,完全不符合Python语法规范

修复步骤

1. 关联防御方对应生命值

在perform_attack函数中,需要根据传入的defender参数,判断要修改的是player1_health还是player2_health,再执行生命值扣除操作。

2. 修正攻击逻辑代码

替换错误的扣除代码,改为根据防御方匹配对应的生命值列表,执行合法的减法运算:

# 替换原来的错误行
if defender == player1_name:
    player1_health[0] -= magnitude
else:
    player2_health[0] -= magnitude

3. 优化:限制生命值下限

为避免生命值出现负数,可在扣除后将生命值限制为0:

if defender == player1_name:
    player1_health[0] = max(0, player1_health[0] - magnitude)
else:
    player2_health[0] = max(0, player2_health[0] - magnitude)

修复后的完整代码

import random
        
def get_valid_name(existing_names):
    while True:
        name = input("Please type your hero’s name: ")
        if name and name not in existing_names:
            return name
        elif name in existing_names:
            print(f"{name} is taken, please choose another name!")

def perform_attack(attacker: any,
                   defender: any) -> None:
    magnitude = int(input(f"————— {attacker} Attacks !! —————\nChoose your attack magnitude between 1 and 50: "))
    
    if 1 <= magnitude <= 50:
        success_chance = random.randint(1, 100)
        if success_chance <= (100 - magnitude):
            print(f"{attacker} hits {magnitude} damage!!!")
            # 修复:根据防御方正确扣除生命值
            if defender == player1_name:
                player1_health[0] = max(0, player1_health[0] - magnitude)
            else:
                player2_health[0] = max(0, player2_health[0] - magnitude)
        else:
            print(f"Ooopsy! {attacker} missed the attack!")
        print_status(player1_name, player2_name)
    else:
        print("The attack magnitude must be between 1 and 50. Choose your attack magnitude between 1 and 50:")

def print_status(player1, player2):
    print(f"\n{player1} {' ' * 57} {player2}\nHP[{player1_health[0]}]: {'I' * (player1_health[0] // 2)} "
          f"HP[{player2_health[0]}]: {'I' * (player2_health[0] // 2)}")

def coin_toss():
    return random.choice([player1_name, player2_name])

def game_over():
    print("#" * 70)
    print(f"{winner} Wins !!!")
    print("#" * 70)
    print("\nThanks for playing! See you again!")

player1_name = get_valid_name([])
player2_name = get_valid_name([player1_name])

player1_health = [100]
player2_health = [100]

current_player = coin_toss()
print(f"Coin toss result: {current_player} starts first!")
print_status(player1_name, player2_name)

while True:
    if current_player == player1_name:
        perform_attack(player1_name, player2_name)
        if player2_health[0] <= 0:
            winner = player1_name
            game_over()
            break
        current_player = player2_name
    else:
        perform_attack(player2_name, player1_name)
        if player1_health[0] <= 0:
            winner = player2_name
            game_over()
            break
        current_player = player1_name

    play_again = input("Do you want to play another round (Yes or No)? ").lower()
    if play_again != 'yes':
        print("\nThanks for playing! See you again!")
        break
    else:
        player1_health = [100]
        player2_health = [100]
        current_player = coin_toss()
        print(f"Coin toss result: {current_player} starts first!")
        print_status(player1_name, player2_name)

额外说明

  • 使用列表存储生命值(如player1_health = [100])是因为列表是可变类型,函数中修改列表元素会直接影响全局变量的值
  • 加入max(0, ...)是为了保证生命值不会出现负数,避免状态显示异常

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.04 05:35:09