深度优先&广度优先(多继承)

Posted xiaohei001

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了深度优先&广度优先(多继承)相关的知识,希望对你有一定的参考价值。

Python支持多父类的继承机制,所以需要注意圆括号中基类的顺序,若是基类中有相同的方法名,并且在子类使用时未指定,Python会从左至右搜索基类中是否包含该方法。一旦查找到则直接调用,后面不再继续查找。

# 父类定义
class people:

    def __init__(self, name, age, weight):
        self.name = name
        self.age = age
        self.__weight = weight

    def speak(self):
        print("%s 说: 我 %d 岁。" % (self.name, self.age))

# 单继承示例
class student(people):

    def __init__(self, name, age, weight, grade):
        # 调用父类的实例化方法
        people.__init__(self, name, age, weight)
        self.grade = grade

    # 重写父类的speak方法
    def speak(self):
        print("%s 说: 我 %d 岁了,我在读 %d 年级" % (self.name, self.age, self.grade))

s = student(ken, 10, 30, 3)
s.speak()

Python3的继承机制

Python3的继承机制不同于Python2。其核心原则是下面两条,请谨记!

  • 子类在调用某个方法或变量的时候,首先在自己内部查找,如果没有找到,则开始根据继承机制在父类里查找。
  • 根据父类定义中的顺序,以深度优先的方式逐一查找父类!

例一:

设想有下面的继承关系:

技术分享图片

class D:
    pass

class C(D):
    pass

class B(C): 
    def show(self):
        print("i am B")
    pass

class G:
    pass

class F(G):
    pass

class E(F): 
    def show(self):
        print("i am E")
    pass

class A(B, E):
    pass

a = A()
a.show()

运行结果是"i am B"。在类A中,没有show()这个方法,于是它只能去它的父类里查找,它首先在B类中找,结果找到了,于是直接执行B类的show()方法。可见,在A的定义中,继承参数的书写有先后顺序,写在前面的被优先继承。

那如果B没有show方法,而是D有呢?

class D:
    def show(self):
        print("i am D")
    pass

class C(D):
    pass

class B(C):

    pass

class G:
    pass

class F(G):
    pass

class E(F): 
    def show(self):
        print("i am E")
    pass

class A(B, E):
    pass

a = A()
a.show()

执行结果是"i am D",左边具有深度优先权,当一条路走到黑也没找到的时候,才换另一条路。可见,在这种继承结构关系中,搜索顺序是这样的:

技术分享图片

例二:

那如果继承结构是这样的呢?类D和类G又同时继承了类H。当只有B和E有show方法的时候,无疑和上面的例子一样,找到B就不找了,直接打印"i am B"。但如果是只有H和E有show方法呢?

技术分享图片

class H:
    def show(self):
        print("i am H")
    pass

class D(H):
    pass

class C(D):
    pass

class B(C):
    pass

class G(H):
    pass

class F(G):
    pass

class E(F): 
    def show(self):
        print("i am E")
    pass

class A(B, E):
    pass

a = A()
a.show()

我们想当然地以为会打印"i am H",因为深度优先嘛。但是,打印的却是"i am E"!为什么?因为在这种情况下,Python的搜索路径是这样的:

技术分享图片

那可能有人会问,别的继承情况呢?这两种继承图太简单了,不能代表所有!实际上其它的继承模式,仔细一解剖,都能划分成上面两种情况,比如下面的例子(箭头代表继承关系),B同时继承了C和F:

class D():
    pass

class G():
    def show(self):
        print("i am G")
    pass

class F(G):
    pass

class C(D):
    pass

class B(C,F):
    pass

class E(F):
    def show(self):
        print("i am E")
    pass

class A(B, E):
    pass

我们用图形来分析它,就是下面的样子:

技术分享图片

 

以上是关于深度优先&广度优先(多继承)的主要内容,如果未能解决你的问题,请参考以下文章

应对笔试手写代码,如何准备深度优先算法 & 广度优先算法?

Python算法-深度优先搜索&广度优先搜索(DFS&BFS)

Python类-多继承的区别

初始继承之顺序/深度优先及广度优先

十深度优先 && 广度优先

经典类深度优先,新式类是广度优先