gpt4 book ai didi

Python 3 __getattribute__ 与点访问行为

转载 作者:太空宇宙 更新时间:2023-11-04 08:01:37 26 4
gpt4 key购买 nike

我阅读了一些关于 python 的对象属性查找的内容(此处:https://blog.ionelmc.ro/2015/02/09/understanding-python-metaclasses/#object-attribute-lookup)。

看起来很简单,所以我试了一下(python3):

class A:
def __getattr__(self, attr):
return (1,2,3)

a = A()

a.foobar #returns (1,2,3) as expected
a.__getattribute__('foobar') # raises AttributeError

我的问题是,这两者不应该是相同的吗?

为什么第二个会引发属性错误?

显然答案是 a.foobar 的逻辑与 a.__getattribute("foobar") 的逻辑不同。根据data model : a.foobar 调用 a.__getattribute("foobar") 如果它引发 AttributeError,它调用 a.-__getattr__('foobar')

看来这篇文章的图表有误。这是正确的吗?

还有一个问题:a.foobar 的真正逻辑在哪里?我认为它在 __getattribute__ 中,但显然不完全是。

编辑:不是的重复

Difference between __getattr__ vs __getattribute__ .我在这里问 object.fooobject.__getattribute__("foo") 有什么区别。这与 __getattr____getatribute__ 不同,后者很简单......

最佳答案

很容易产生这样的印象,即 __getattribute__ 比实际负责的更多。 thing.attr 不会直接转换为 thing.__getattribute__('attr'),并且 __getattribute__ 不负责调用 __getattr__

回退到 __getattr__ 发生在位于 __getattribute__ 之外的属性访问机制部分。属性查找过程是这样的:

  • 通过直接搜索对象类型的 MRO 找到 __getattribute__ 方法,绕过常规属性查找过程。
  • 试试 __getattribute__
    • 如果 __getattribute__ 返回了一些东西,属性查找过程就完成了,那就是属性值。
    • 如果 __getattribute__ 引发非 AttributeError,则属性查找过程完成,并且异常传播到查找之外。
    • 否则,__getattribute__ 会引发 AttributeError。查找继续。
  • 以与查找 __getattribute__ 相同的方式查找 __getattr__ 方法。
    • 如果没有__getattr__,则属性查找过程完成,并且传播来自__getattribute__ 的AttributeError。
  • 尝试 __getattr__,并返回或提高任何 __getattr__ 返回或提高的值。

至少,就语言语义而言,它是这样工作的。在低级实现方面,其中一些步骤在不需要的情况下可能会被优化掉,还有像 tp_getattro 这样的 C 钩子(Hook)我没有描述。除非您想深入研究 CPython 解释器源代码,否则您无需担心此类事情。

关于Python 3 __getattribute__ 与点访问行为,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39043912/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com