Python 继承:何时以及为什么 __init__

use*_*991 5 python inheritance

我是 Python 新手,试图了解继承方法背后的哲学/逻辑。问题最终涉及为什么以及何时必须__init__在子类中使用该方法。例子:

从超类继承的子类似乎不需要自己的构造函数(__init__) 方法。下面,一只狗继承了哺乳动物的属性(名字、年龄)和方法(makenoise)。你甚至可以添加一个方法 ( do_a_trick) 一切都像它“应该的”那样工作,看起来。

但是,如果我想在子类中添加一个新属性,就像我在 Cats 类中所做的那样,我会收到一条错误消息,指出“self”未定义。然而,我在狗类的定义中使用了“自我”。区别的本质是什么?它似乎定义了 Cats,因为我希望我需要使用__init__(self,name)super()__init__(name)。为什么会有差异?

class Mammals(object):

  def __init__(self,name):
    self.name = name
    print("I am a new-born "+ self.name)  
    self.age = 0

  def makenoise(self):
    print(self.name + " says Hello")

class Dogs(Mammals):

  def do_a_trick(self):
    print(self.name + " can roll over")

class Cats(Mammals):

 self.furry = "True"  #results in error `self' is not defined


mymammal = Mammals("zebra") #output "I am a new-born zebra"
mymammal.makenoise()  #output "zebra says hello"
print(mymmmal.age)    #output 0

mydog = Dogs("family pet") #output "I am a new-born family pet"
mydog.makenoise()  #output "family pet says hello"
print(mydog.age)  # output 0
mydog.do_a_trick() #output "family pet can roll over"
Run Code Online (Sandbox Code Playgroud)

Jon*_*sky 3

如果我想像在 Cats 类中尝试那样在子类中添加新属性,则会收到一条错误消息,指出“self”未定义。然而我在狗类的定义中使用了“self”。

在你的超类 Mammal 中,你有一个__init__函数,它接受一个你选择*调用的参数self。当您位于函数体中时,此参数就在范围内__init__- 它是一个像任何局部变量一样的局部变量,并且在包含它的函数终止后不可能引用它。Dog 类上定义的函数do_a_trick也采用名为 的参数self,并且它也是该函数的本地函数。这些变量的特殊之处不是它们的名称(您可以随意称呼它们),而是事实上,作为 python 中实例方法的第一个参数,它们获得对调用它们的对象的引用作为它们的值。(最后一句话再读几遍,这是理解这一点的关键,第一次你可能不会明白。)

现在,在 中Cat,您有一行代码根本不在函数中。此时范围内没有任何内容,包括self,这就是失败的原因。如果您要定义一个Cat带有名为 的参数的函数self,则可以引用该参数。如果该参数恰好是 实例方法的第一个参数Cat,那么它将具有 实例的值Cat,那么它将具有调用它的否则,它就会拥有传递给它的任何东西。

*你的选择是明智的!