【发布时间】:2020-01-04 19:59:58
【问题描述】:
注意此问题已在 cmets 中得到解答
我注意到__getattribute__ 和__getattr__ 中的一些异常处理行为,我在文档或此处的其他帖子中找不到。
考虑这个类A。如果A 的实例具有None 属性,则访问该属性会引发AttributeError。
class A:
def __getattribute__(self, item):
value = object.__getattribute__(self, item)
if value is None:
raise AttributeError('in __getattribute__')
return value
def __init__(self, a=None):
self.a = a
A(1).a # 1
A().a # raises AttributeError('in __getattribute__')
现在,__getattribute__ 上的 docs 说
无条件调用以实现类实例的属性访问。如果该类还定义了
__getattr__(),则不会调用后者,除非__getattribute__()明确调用它或引发AttributeError。
由此,我猜想__getattribute__ 中引发的任何AttributeError 总是会被捕获,并且该过程会延迟到__getattr__,这样调用者就永远不会看到AttributeError('in __getattribute__')。
令我惊讶的是,不仅看到了错误,而且在A().a 上引发的AttributeError 是__getattribute__ 中的错误,好像从未调用过__getattr__。那是 除非 __getattr__ 提出自己的
def __getattr__(self, item):
raise AttributeError('in __getattr__')
在这种情况下,我们会看到 AttributeError('in __getattr__') 被提升。
这里有什么规则?如果我在__getattribute__ 中提出AttributeError 的一些子类Oops 而不是AttributeError('in __getattribute__'),它们是否适用?
【问题讨论】:
-
If the class also defines __getattr__()- 你的班级没有定义__getattr__ -
@snakecharmerb 很好奇,继承自
object的__getattr__会发生什么? -
奇怪 -
object上没有__getattr__(试试object.__getattr__)。那么object.__getattr__的文档是什么意思? -
ah, "可以定义以下方法来自定义类实例的属性访问(使用、分配或删除 x.name)的含义。"
-
那么这里有什么问题呢?我没有看到。
标签: python exception python-datamodel