python mro c3_python -- MRO C3算法

classA:pass

classB(A):pass

classC(A):pass

classD(B, C):pass

classE(C, A):pass

classF(D, E):pass

classG(E):pass

classH(G, F):pass

⾸先. 我们要确定从H开始找. 也就是说. 创建的是H的对象

⾸首先. 我们要确定从H开始找. 也就是说. 创建的是H的对象.     如果从H找. 那找到H+H的⽗父类的C3, 我们设C3算法是L(x) , 即给出x类. 找到x的MRO

L(H) = H + L(G) + L(F) + GF

继续从代码中找G和F的⽗父类往⾥里里⾯面带

L(G) = G + L(E) + E

L(F) = F + L(D)+ L(E) + DE

继续找E 和 D

L(E) = E + L(C) + L(A) + CA

L(D) = D + L(B) + L(C) + BC

继续找B和C

L(B) = B + L(A) + A

L(C) = C + L(A) + A

最后就剩下⼀一个A了了. 也就不⽤用再找了了. 接下来. 把L(A) 往⾥里里带. 再推回去. 但要记住. 这⾥里里的 + 表⽰示的是merge.

merge的原则是⽤用每个元组的头⼀一项和后⾯面元组的除头⼀一项外的其他元 素进⾏行行比较, 看是否存在. 如果存在.

就从下⼀一个元组的头⼀一项继续找. 如果找不到. 就拿出来. 作为merge的结果的⼀一项. 以此类推. 直到元组之间的元素都相同. 也就不⽤用再找了了.

L(B) =(B,) + (A,) + (A) -> (B, A)

L(C) =(C,) + (A,) + (A) -> (C, A)

继续带.

L(E) = (E,) + (C, A) + (A)  + (C,A) -> E, C, A

L(D) = (D,) + (B, A) + (C, A)  + (B, C) -> D, B, C, A

继续带.

L(G) = (G,) + (E, C, A) + (E) -> G, E, C, A

L(F) = (F,) + (D, B, C, A) + (E, C, A)  + (D, E)-> F,  D, B,  E, C, A

加油, 最后了了

L(H) = (H, ) + (G, E, C, A) + ( F,  D,  B,  E, C, A) + (G, F) -> H, G, F, D, B, E, C,

验证

使⽤用类名.__mro__获取到类的MRO信息.

(, , , ,

, , , , )

C3是把我们多个类产生的共同继承留到最后去找,所以,我们也可以从图上来看到相关的规律,这个要大家自己多谢多画图就可以感觉到。但是如果没有所谓的共同继承关系。那几乎就当成是深度遍历就可以了。

4、super() 找MRO顺序的下一个

super()可以帮我们执行MRO中下一个父类的方法,通常super()有两个使用的地方:

1、可以访问父类的构造方式

2、当子类方法想调用父类(MRO)中的方法

第一种

classFoo:def __init__(self,a,b,c):

self.a=a

self.b=b

self.c=cclassBar(Foo):def __init__(self,a,b,c,d):

super().__init__(a,b,c) #访问父类的构造方法

self.d =d

b= Bar(1,2,3,4)print(b.__dict__)#{'a': 1, 'b': 2, 'c': 3, 'd': 4}

第二种

classFoo:deffunc1(self):

super().func1()#此时要找的是MRO顺序中下一个类的func1()方法

print("我的老家就住在这个屯")classBar:deffunc1(self):print("你的老家不在这个屯")classKu(Foo,Bar):deffunc1(self):

super().func1()#此时super找的是Foo

print("他的老家不知道在哪个屯")

k= Ku() #先看MRO,Ku,Foo,Bar,object

k.func1()#你的老家不在这个屯#我的老家就住在这个屯#他的老家不知道在哪个屯

5、一道面试题

#MRO + super 面试题

classInit(object):def __init__(self, v):print("init")

self.val=vclassAdd2(Init):def __init__(self, val):print("Add2")

super(Add2, self).__init__(val)print(self.val)

self.val+= 2

classMult(Init):def __init__(self, val):print("Mult")

super(Mult, self).__init__(val)

self.val*= 5

classHaHa(Init):def __init__(self, val):print("哈哈")

super(HaHa, self).__init__(val)

self.val/= 5

classPro(Add2,Mult,HaHa):pass

classIncr(Pro):def __init__(self, val):

super(Incr, self).__init__(val)

self.val+= 1

#Incr Pro Add2 Mult HaHa Init

p = Incr(5)print(p.val)

c= Add2(2)print(c.val)#Add2#Mult#哈哈#init#5.0#8.0#Add2#init#2#4

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值