python 中的super()继承,搜索广度为先

一、python中类的继承
1.1 单继承

在python 中我们可以这样来定义一个类:及继承它的子类

class Father:

    def __init__(self, mes):       #1 父类的init构造方法
        print('From Father. form {}'.format(mes))

class Child(Father):

    def __init__(self, message, personal):     #2 子类的构造方法
        Father.__init__(self, message)       #3 继承父类构造方法
        print("I'm child. From {}".format(personal))

c = Child('儿子', '拼爹')

#执行结果为
From Father. form 儿子     #4
I'm child. From 拼爹      #5

在这个列子中,子类 Child 继承父类 Father,并在#2 自己的构造方法#3处中继承父类的构造方法,先执行完#3处继承父类#1的构造放方法得到结果#4,然后继续执行自身构造方法输出#5

1.2 help(super) 看下super有些什么
>>> help(super)

Help on class super in module builtins:

class super(object)
 |  super() -> same as super(__class__, <first argument>)
 |  super(type) -> unbound super object
 |  super(type, obj) -> bound super object; requires isinstance(obj, type)
 |  super(type, type2) -> bound super object; requires issubclass(type2, type)
 |  Typical use to call a cooperative superclass method:
 |  class C(B):
 |      def meth(self, arg):
 |          super().meth(arg)
 |  This works for class methods too:
 |  class C(B):
 |      @classmethod
 |      def cmeth(cls, arg):
 |          super().cmeth(arg)
 |  
 |  Methods defined here:
 |  
 #...........后面还有很多,没什么好讲的,这儿就够了
1.3 super的使用
  1. super() #另一个写法 super('class_name', self)
  2. super(type)
  3. super(type, obj)
  4. super(type, type2)

推荐第一种写法,方便

class A:
  def __init__(self):
    print("From A")


class B(A):
  def __init__(self):
    super().__init__()     #1 这儿还有个写法super(B, self).__init__()
    print("From B")


b = B()

#结果为
From A
From B

单继承下乍看没区别,的确。可是当考虑到多继承时

二、多继承
2.1 多继承下深度为先
class A:
    def __init__(self):
        print("From A")
        print("END A")

class B(A):
    def __init__(self):
        print("From B")
        A.__init__(self)
        print("END B")

class C(A):
    def __init__(self):
        print("From C")
        A.__init__(self)
        print("END C")

class D(A):
    def __init__(self):
        print("From D")
        A.__init__(self)
        print("END D")

class E(B, C, D):
    def __init__(self):
        print("From E")
        B.__init__(self)
        C.__init__(self)
        D.__init__(self)
        print("END E")

E()

#结果为
From E
From B
From A
END A
END B
From C
From A
END A
END C
From D
From A
END A
END D
END E

首先可以看到,E当中继承顺序是 B、C、D,
然后搜索顺序则为先到第一个继承的E-->B-->A -->C-->A -->D-->A 深度为先。然后结果大家也看到了,这样的继承方式会导致A被执行很多遍。

2.2、super继承 广度为先

super的使用方式有两种:

  1. super()init()
  2. super(类名, self).__init__()
class A:
    def __init__(self):
        print("From A")
        print("END A")

class B(A):
    def __init__(self):
        print("From B")
        super().__init__()
        print("END B")

class C(A):
    def __init__(self):
        print("From C")
        super(C, self).__init__()
        print("END C")

class D(A):
    def __init__(self):
        print("From D")
        super(D, self).__init__()
        print("END D")

class E(B, C, D):
    def __init__(self):
        print("From E")
        super().__init__()
        print("END E")

E()  #1 继承顺序

print(E.__mro__)     #2 查看super类里面维护的继承顺序

#-结果为:

From E
From B
From C
From D
From A
END A
END D
END C
END B
END E
(<class '__main__.E'>, <class '__main__.B'>, <class '__main__.C'>, <class '__main__.D'>, <class '__main__.A'>, <class 'object'>) #3

可以看到#1处E(B, C, D)的继承查找顺序就为 E-->B-->C-->D-->A 通过#2处
E.__mro__属性也可以看到,super自己维护的顺序为#3最后的列表 E-->B-->C-->D-->A--object(所有新式类的基类)
是一样的。因为它就是按照__mro__来寻找的

转载于:https://www.cnblogs.com/shiqi17/p/9469721.html

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值