在父类中访问子类的变量是否正确?这是一种好的 OOP 方法吗?我不需要创建 Animal 类的实例,但如果我愿意的话,make_sound
方法会提高AttributeError
,这让我很困扰。
class Animal:
def make_sound(self):
print(self.sound)
class Cat(Animal):
sound = 'meow'
class Dog(Animal):
sound = 'bark'
cat = Cat()
cat.make_sound()
dog = Dog()
dog.make_sound()
这种方法本质上没有什么问题。这实际上取决于此类的范围和重要性以及它的使用位置。构建父类以使用隐式定义的属性非常快,并且在许多情况下完全没问题。但是,有时这些隐式属性可能会失控,您可能希望确保任何创建新子类的人has来定义这些属性。
有几种方法可以实现这一点。其中一些可能不起作用,具体取决于您使用的 Python 版本。我相信像这样的 ABC 用法可以在 Python 3.4+ 中使用。
Python(以及许多面向对象语言)有一个概念抽象基类 https://docs.python.org/3/library/abc.html。这是一个永远无法实例化的类,它强制任何子类必须实现定义为抽象的方法或属性才能实例化。
您可以通过以下方式提供make_sound
方法,并且仍然 100% 确定任何对 Animal 进行子类化的人确实发出了这种声音。
from abc import ABC, abstractmethod
class Animal(ABC):
def make_sound(self):
print(self.sound)
@property
@abstractmethod
def sound(self):
""" return the sound the animal makes """
class Dog(Animal):
@property
def sound(self):
return "bark"
class Cat(Animal):
sound = "meow"
class Thing(Animal):
""" Not an animal """
dog = Dog()
dog.make_sound()
cat = Cat()
cat.make_sound()
# thing = Thing() this will raise a TypeError, complaining that its abstract
# animal = Animal() as will this
这显示了执行此操作的许多不同方法。使用@property
装饰器允许您设置影响它的实例变量或更复杂的逻辑。在类中设置声音(有点)类似于在 Java 类中设置静态成员。由于所有的猫都会喵喵叫,因此在这种情况下这可能是有道理的。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)