3

是否有令人信服的理由来调用type.mro()而不是直接迭代type.__mro__?访问速度实际上快了约 13 倍(36ns vs 488ns)

我在寻找缓存时偶然发现了它type.mro()。这似乎是合法的,但它让我想知道:我可以依靠type.__mro__,还是必须打电话type.mro()?在什么情况下我可以摆脱前者?

更重要的是,必须发生哪些条件type.__mro__才能无效?

例如,当定义/创建一个改变现有类的 mro 的新子类时,现有类是否会.__mro__立即更新?每次创建新班级时都会发生这种情况吗?这使它成为类类型的一部分?哪一部分?..或者这type.mro()是关于什么的?

当然,所有这些假设type.__mro__实际上是一个缓存名称的元组,它们指向给定类型的 mro 中的对象。如果该假设不正确;那这是什么?(可能是描述符或其他东西..)为什么我可以/不能使用它?

编辑:如果它是一个描述符,那么我很想学习它的魔力,因为两者都是:type(type.__mro__) is tupletype(type(type).__mro__) is tuple(即:可能不是描述符)

编辑:不确定这有多相关,但type('whatever').mro()返回一个列表,而type('whatever').__mro__返回一个元组。(不?)幸运的是,附加到该列表不会更改对相关类型(在本例中为 str)的__mro__或后续调用。.mro()

谢谢您的帮助!

4

1 回答 1

4

根据文档

class.__mro__

此属性是在方法解析期间查找基类时考虑的类元组。

class.mro()

元类可以重写此方法,以自定义其实例的方法解析顺序。它在类实例化时调用,其结果存储在__mro__.

所以是的,您关于__mro__成为缓存的假设是正确的。如果你的元类mro()总是返回相同的东西,或者你没有任何元类,你可以安全地使用__mro__.

于 2015-09-03T04:33:26.770 回答