1.MRO表 返回类型方法顺序的解析表 C3算法计算: class B(O) --> mro(B) = [B, O] class B(A1, A2, ...) --> mro(B) =
1.MRO表
返回类型方法顺序的解析表
C3算法计算:
class B(O) --> mro(B) = [B, O]
class B(A1, A2, ...) --> mro(B) = [B] + merge(mro(A1), mro(A2), ... , [A1, A2, ...])
顺序遍历列表
首元素满足以下条件,否则遍历下一个序列
在其他序列也是首元素
在其他序列里不存在
从所有序列中移除此元素,合并到MRO序列中
重复执行,直到所有序列为空或无法执行下去
通过树理解:
如果有以下继承关系:
object / / / A | / / B-1 C-2 D-2 / / / E-1 / / / F
F的MRO表的计算过程就是:
L(O) = OL(B) = B OL(A) = A OL(C) = C A OL(D) = D A OL(E) = E + merge(L(B),L(C)) # merger顺序是继承顺序 = E + merge(BO,CAO) # B的父类是O,C的父类A的父类O,B和C同层继承,由于E继承B和C时,B在A前 = E + B + merge(O,CAO) = E + B + C + merge(O,AO) = E + B + C + A + merge(O,O) = E B C A OL(F) = F + merge(L(E),L(D)) = F + merge(EBCAO,DAO) # EBC在DAO中不存在 = F + EBC + merge(AO,DAO) # A在DAO中存在,D在AO中不存在 = F + EBC + D + merge(AO,AO) # 同时移除AO = F EBC D AO
MRO:
F -> E -> B -> C -> D -> A -> object
MRO计算原则有:
1.基类永远在派生类后面
2.类继承的顺序影响MRO的顺序
继承时要满足MRO表,否则抛出无法写入MRO表异常
2.super
在调用父类方法的过程中,因为继承,子类要先初始化父类的方法,就会导致调用父类的方法会多调用父类的父类的方法
使用super方法调用,可以避免
super() -> same as super(__class__, <first argument>)super(type, obj) -> bound super object; requires isinstance(obj, type)super(type) -> unbound super objectsuper(type, type2) -> bound super object; requires issubclass(type2, type)Typical use to call a cooperative superclass method
super通过返回指代type下一个父类的super对象,进行调用父类方法
super方法类似于:
def super(cls, inst): mro = inst.__class__.mro() return mro[mro.index(cls) + 1]
通过MRO表往下指代