7

在下面的示例中,x即使x存在于对象的插槽中,也可以从对象的插槽中访问属性__dict__(这不是典型或可能有用的情况,但我很好奇):

>>> class C(object):
...     __slots__ = 'x'
...     
>>> class D(C):
...     pass
... 
>>> obj = D()
>>> obj.x = 'Stored in slots'
>>> obj.__dict__
{}
>>> obj.__dict__['x'] = 'stored in __dict__'
>>> obj.x
'Stored in slots'

这种访问顺序(插槽优先)是记录在案的行为吗?或者只是一个实现细节?

4

1 回答 1

11

是的,__dict__只有在查阅了数据描述符之后才会查阅对象的 。__slots__属性被实现为数据描述符。

请参阅调用描述符

例如绑定,描述符调用的优先级取决于定义的描述符方法。描述符可以定义和__get__()的任意组合。如果未定义,则访问该属性将返回描述符对象本身,除非该对象的实例字典中有值。如果描述符定义和/或,它是一个数据描述符;如果两者都没有定义,则它是非数据描述符。通常,数据描述符定义了and ,而非数据描述符只有方法。带有和定义的数据描述符总是覆盖实例字典中的重新定义。相反,非数据描述符可以被实例覆盖。__set__()__delete__()__get__()__set__()__delete__()__get__()__set__()__get__()__set__()__get__()

并在同一页面上,关于插槽的部分

__slots__通过为每个变量名创建描述符(实现描述符)在类级别实现。因此,类属性不能用于设置由__slots__;定义的实例变量的默认值。否则,类属性将覆盖描述符分配。

于 2013-02-28T15:22:03.080 回答