0

我尝试实现装饰器模式。Hero是不能改变的主类,然后我有AbstractEffects,它是Hero的子类和AbstractNegative和AbstractPositive的父类。另一方面,AbstractNegative 和 AbstractPositive 是 Curse、Berserk 等的父类。

from abc import ABC, abstractmethod
class Hero():
    def __init__(self):
        self.positive_effects = []
        self.negative_effects = []
        self.stats = {
            "HP": 128,  # health points
            "MP": 42,  # magic points, 
            "SP": 100,  # skill points
            "Strength": 15,  # сила
            "Perception": 4,  # восприятие
            "Endurance": 8,  # выносливость
            "Charisma": 2,  # харизма
            "Intelligence": 3,  # интеллект
            "Agility": 8,  # ловкость 
            "Luck": 1  # удача
        }
    def get_positive_effects(self):
        return self.positive_effects.copy()
    def get_negative_effects(self):
        return self.negative_effects.copy()
    def get_stats(self):
        return self.stats.copy()

class AbstractEffects(ABC, Hero):
    def __init__(self, base):
        self.base = base 
    @abstractmethod
    def get_positive_effects(self):
        return self.positive_effects.copy()
    @abstractmethod
    def get_negative_effects(self):
        return self.negative_effects.copy()
    @abstractmethod
    def get_stats(self):
        return self.stats.copy()

class AbstractPositive(AbstractEffects):
    def get_positive_effects(self):
        return self.base.positive_effects.copy()
    def get_negative_effects(self):
        return self.base.negative_effects.copy()

class AbstractNegative(AbstractEffects):  
    def get_positive_effects(self):
        return self.base.positive_effects.copy()
    def get_negative_effects(self):
        return self.base.negative_effects.copy()

class Berserk(AbstractEffects):
    def get_stats(self):
        self.base.stats["Strength"] = int(self.base.stats["Strength"]) + 2
        self.base.stats["Endurance"] = int(self.base.stats["Endurance"]) + 7
        self.base.stats["Agility"] = int(self.base.stats["Agility"]) + 7
        self.base.stats["Luck"] = int(self.base.stats["Luck"]) + 7
        self.base.stats["Perception"] = int(self.base.stats["Perception"]) - 3
        self.base.stats["Charisma"] = int(self.base.stats["Charisma"]) - 3
        self.base.stats["Intelligence"] = int(self.base.stats["Intelligence"]) - 3
        self.base.stats["HP"] = int(self.base.stats["HP"]) + 50
        return self.base.stats.copy()

    def get_positive_effects(self):
        self.base.positive_effects.append("Blessing")
        return self.base.positive_effects.copy()
    def get_negative_effects(self):
        try:
            return self.base.negative_effects.pop()
        except:
            return self.base.negative_effects.copy()

class Blessing(AbstractPositive):
    def get_stats(self):
        self.base.state["Strength"] = int(self.base.state["Strength"]) + 2
        self.base.state["Endurance"] = int(self.base.state["Endurance"]) +2
        self.base.state["Agility"] = int(self.base.state["Agility"]) + 2
        self.base.state["Luck"] = int(self.base.state["Luck"]) + 2
        self.base.state["Perception"] = int(self.base.state["Perception"]) + 2
        self.base.state["Charisma"] = int(self.base.state["Charisma"]) + 2
        self.base.state["Intelligence"] = int(self.base.state["Intelligence"]) + 2
        return self.base.state.copy()
    def get_positive_effects(self):
        self.base.positive_effects.append("Blessing")
        return self.basepositive_effects.copy()
    def get_negative_effects(self):
        try:
            return self.base.negative_effects.pop()
        except:
            return self.base.negative_effects.copy()

class Weakness(AbstractNegative):
    def __init__(self, obj):
        self.base.stats = obj.copy()
    def get_stats(self):
        self.base.stats["Strength"] = int(self.base.stats["Strength"]) - 4
        self.base.stats["Endurance"] = int(self.base.stats["Endurance"]) - 4
        self.base.stats["Luck"] = int(self.base.stats["Luck"]) - 4
        return self.base.stats.copy
    def get_positive_effects(self):
        try:
            return self.base.positive_effects.pop()
        except:
            return self.base.positive_effects.copy()
    def get_negative_effects(self):
        self.base.stats.negative_effects.append("Weaknes")
        return  self.base.stats.negative_effects.copy()

class EvilEye(AbstractNegative):
    def get_stats(self):
        self.base.stats["Luck"] = int(self.base.stats["Luck"]) - 10
        return self.base.stats.copy()
    def get_positive_effects(self):
        try:
            return self.base.positive_effects.pop()
        except:
            return self.base.positive_effects.copy()
    def get_negative_effects(self):
        self.base.negative_effects.append("EvilEye")
        return self.base.negative_effects.copy()

class Curse(AbstractNegative):
    def get_stats(self):
        self.base.stats["Strength"] = int(self.base.stats["Strength"]) - 2
        self.base.stats["Endurance"] = int(self.base.stats["Endurance"]) -2
        self.base.stats["Agility"] = int(self.base.stats["Agility"]) - 2
        self.base.stats["Luck"] = int(self.base.stats["Luck"]) - 2
        self.base.stats["Perception"] = int(self.base.stats["Perception"]) - 2
        self.base.stats["Charisma"] = int(self.base.stats["Charisma"]) - 2
        self.base.stats["Intelligence"] = int(self.base.stats["Intelligence"]) - 2
        return self.base.stats.copy()
    def get_positive_effects(self):
        try:
            return self.base.positive_effects.pop()
        except:
            return self.base.positive_effects.copy()
    def get_negative_effects(self):
        self.base.stats.negative_effects.append("Curse")
        return  self.base.stats.negative_effects.copy()

当我尝试这样做时

hero = Hero()
hero.get_stats()
brs1 = Berserk(hero)
brs1.get_stats()
brs2 = Berserk(brs1)
cur1 = Curse(brs2)
cur1.get_stats()

我有这个错误:“AttributeError:'Berserk'对象没有属性'stats'”我无法理解如何解决这个错误。

4

1 回答 1

0

如果定义 的__init__子类的方法Hero,则需要调用超类的__init__方法Hero,以初始化 定义的属性Hero.__init__,包括stats在这种情况下:

class Berserk(Hero):
    def __init__(self):
        super().__init__()
        # additional initialization for a Berserk instance
于 2019-12-13T20:32:47.733 回答