分类目录:《系统学习Python》总目录
文章《系统学习Python——装饰器:“私有“和“公有“属性案例-[实现私有属性]》中的代码中__setattr__
方法依赖于一个实例对象的__dict__
属性命名空间字典,以设置onlnstance
自己的wrapped
属性。正如我们在之前的文章中所了解到的,这一方法不能在没有循环的情况下直接赋值一个属性。然而,它使用了__setattr__
内置函数而不是__dict__
字典来设置被包装对象自身之中的属性。此外,__getattr__
用来获取被包装对象中的属性,因为它们可能存储在对象自身中或者由对象继承。
因此,这段代码将对大多数类有效,包括那些带有基于slot
、property
、描述符的“虚拟"类级别属性,甚至还包括__setattr__
及其同类。通过只为它自己设定一个命名空间字典,并且为被包装的对象使用存储中立的工具,包装器类就可以避免其他工具中的内在局限。
例如,我们可能还知道带有__slots__
的新式类也许不能把属性存储到一个__dict__
中(并且实际上甚至不能在其中存储任何属性)。然而,由于我们在这里只是在onlnstance
层级依赖于一个__dict__
字典,而不是在被包装的实例中,因此这一担忧并不适用。除此以外,因为setattr
和getattr
应用于基于__dict__
和__slots__
的属性,所以我们的装饰器应用于使用任何一种存储方案的类。基于同样的原因,装饰器也适用于新式property
和相似的工具:在被包装实例中委托的名称会被重新查找,而与装饰器代理对象自己的属性无关。
参考文献:
[1] Mark Lutz. Python学习手册[M]. 机械工业出版社, 2018.