欢迎使用CSDN-markdown编辑器

来源:互联网 发布:淘宝蜜琪美妆是假货吗 编辑:程序博客网 时间:2024/06/06 00:31

python super关键字:在子类中调用父类的方法时,单继承时直接使用类名来调用父类方法没有问题,但是中多继承中会产生问题。如下:

class A:def __init__(self):   print "enter A"   print "leave A"class B(A):def __init__(self):   print "enter B"   A.__init__(self)  ## 直接用类名调用父类方法   print "leave B"

b = B()
enter B
enter A
leave A
leave B
即,使用非绑定的类方法(用类名来引用的方法),并在参数列表中,引入待绑定的对象(self),从而达到调用父类的目的。

这样做的缺点是,当一个子类的父类发生变化时(如类B的父类由A变为C时),必须遍历整个类定义,把所有的通过非绑定的方法的类名全部替换过来,例如代码

class B(C): # A –> C
def init(self):
print “enter B”
C.init(self) # A –> C
print “leave B”

这样的改动或许还可以接受。但如果代码量庞大,这样的修改可能是灾难性的。很容易导致修改错误的出现。

class A(object):    # A must be new-style classdef __init__(self):   print "enter A"   print "leave A"class B(C):     # A --> Cdef __init__(self):   print "enter B"   super(B, self).__init__()   print "leave B"

尝试执行上面同样的代码,结果一致,但修改的代码只有一处,把代码的维护量降到最低,是一个不错的用法。

class A:def __init__(self):print("Enter A")print("Leave A")class B(A):def __init__(self):print("Enter B")A.__init__(self)print("Leave B")class C(A):def __init__(self):print("Enter C")A.__init__(self)print("Leave C")class D(A):def __init__(self):print("Enter D")A.__init__(self)print("Leave D")class E(B, C, D):def __init__(self):print("Enter E")B.__init__(self)C.__init__(self)D.__init__(self)print("Leave E")

E()

结果:

Enter E
Enter B
Enter A
Leave A
Leave B
Enter C
Enter A
Leave A
Leave C
Enter D
Enter A
Leave A
Leave D
Leave E

执行顺序很好理解,唯一需要注意的是公共父类A被执行了多次。

代码二:

class A:def __init__(self):print("Enter A")print("Leave A")class B(A):def __init__(self):print("Enter B")super(B, self).__init__()print("Leave B")class C(A):def __init__(self):print("Enter C")super(C, self).__init__()print("Leave C")class D(A):def __init__(self):print("Enter D")super(D, self).__init__()print("Leave D")class E(B, C, D):def __init__(self):print("Enter E")super(E, self).__init__()print("Leave E")

E()

结果:

Enter E
Enter B
Enter C
Enter D
Enter A
Leave A
Leave D
Leave C
Leave B
Leave E

在super机制里可以保证公共父类仅被执行一次,至于执行的顺序,是按照mro进行的(E.mro)。

0 0