153

django.utils.functional.py

for t in type(res).mro():  # <----- this
    if t in self.__dispatch:
        return self.__dispatch[t][funcname](res, *args, **kw)

我不明白mro()。它有什么作用,“mro”是什么意思?

4

4 回答 4

243

跟着...:

>>> class A(object): pass
... 
>>> A.__mro__
(<class '__main__.A'>, <type 'object'>)
>>> class B(A): pass
... 
>>> B.__mro__
(<class '__main__.B'>, <class '__main__.A'>, <type 'object'>)
>>> class C(A): pass
... 
>>> C.__mro__
(<class '__main__.C'>, <class '__main__.A'>, <type 'object'>)
>>> 

只要我们有单继承,__mro__就只是以下的元组:类,它的基,它的基的基,等等object(当然只适用于新式类)。

现在,使用多重继承......:

>>> class D(B, C): pass
... 
>>> D.__mro__
(<class '__main__.D'>, <class '__main__.B'>, <class '__main__.C'>, <class '__main__.A'>, <type 'object'>)

...您还可以保证,在 中__mro__,没有类是重复的,并且没有类在其祖先之后,除了首先进入同一多重继承级别的类(如本例中的 B 和 C)在__mro__左到右。

__mro__你在一个类的实例上获得的每个属性,不仅仅是方法,在概念上都是沿着__mro__定义该名称的那个。

于 2010-01-06T03:17:19.010 回答
92

mro()代表方法解析顺序。它返回类派生的类型列表,按照搜索方法的顺序。

mro()并且__mro__只在新样式类上工作。在 Python 3 中,它们可以正常工作。然而,在 Python 2 中,这些类需要继承自object.

于 2010-01-06T03:08:58.440 回答
16

这可能会显示解决的顺序。

class A(object):
    def dothis(self):
        print('I am from A class')

class B(A):
    pass

class C(object):
    def dothis(self):
        print('I am from C class')

class D(B, C):
    pass

d_instance= D()
d_instance.dothis()
print(D.mro())

和回应将是

I am from A class
[<class '__main__.D'>, <class '__main__.B'>, <class '__main__.A'>, <class '__main__.C'>, <class 'object'>]

规则是深度优先的,在这种情况下意味着 D、B、A、C。

Python 在搜索继承类时通常使用深度优先顺序,但是当两个类从同一个类继承时,Python 会从 mro 中删除该类的第一次提及。

于 2016-03-21T21:47:41.840 回答
3

钻石继承中的解析顺序会有所不同。

class A(object):
    def dothis(self):
        print('I am from A class')


class B1(A):
    def dothis(self):
        print('I am from B1 class')
    # pass


class B2(object):
    def dothis(self):
        print('I am from B2 class')
    # pass


class B3(A):
    def dothis(self):
        print('I am from B3 class')


# Diamond inheritance
class D1(B1, B3):
    pass


class D2(B1, B2):
    pass


d1_instance = D1()
d1_instance.dothis()
# I am from B1 class
print(D1.__mro__)
# (<class '__main__.D1'>, <class '__main__.B1'>, <class '__main__.B3'>, <class '__main__.A'>, <class 'object'>)


d2_instance = D2()
d2_instance.dothis()
# I am from B1 class
print(D2.__mro__)
# (<class '__main__.D2'>, <class '__main__.B1'>, <class '__main__.A'>, <class '__main__.B2'>, <class 'object'>)
于 2018-08-05T13:13:24.767 回答