自定义属性的访问 - Customizing attribute access
1 自定义属性的访问 - Customizing attribute access 2 3 在 python 中, 下列方法可以实现类实例属性 instance.attribute 的 使用,设置,删除. 4 object.__getattr__(self, name) 5 找不到 attribute 的时候被调用(__dict__ 属性中找不到的时候), 6 例如, 所调用的 attribute 不是 instance.attribute, 或者类中没有这个 attribute, 7 即 self.attribute 找不到. 该方法返回的是的 attribute 的 value, 或者 8 raise AttributeError 异常. 9 10 Note, 11 如果 attribute 存在 __dict__ 中, __getattr__ 是不会被调用的. 12 这一点体现了 __getattr__ 与 __setattr__ 的非对称调用, 这种不 13 对称是 python 故意儿为之, 原因有二, 14 a, 为了效率的原因 - 找到 attribute 后,无需浪费资源再'向上(MRO)'查找. 15 b, 如果不这样做 __getattr__ 将无法访问 instance 的其他 attributes. 16 至少对于 instance variables 来说, 可以通过在 __dict__ 中插入变量的值来实现, 17 __dict__[variables] = value,从而得到对该 variables 的访问及控制(total control). 18 上面这样这种做法, 在 python doc 中被称为 'fake total control', 相对应的后面将 19 介绍的 __getattribute__ 方法被称作'actually get total control'. 20 21 object.__getattribute__(self, name) 22 在获取 instances.attribute 的时候无条件的被调用. 23 如果在 instances 所属的 class 中定义了 __getattr__ 方法, __getattr__ 将不会被调用, 24 除非在 __getattribute__ 方法中显示的调用 __getattr__, 或者 __getattribute__ 方法 25 raises AttributeError 异常. 26 为防止无线的递归, 调用 __getattribute__ 方法的时候应该保证始终在 instances 的基类上调用. 27 Note, 28 有种情况可能绕过此方法,即 通过 隐式调用 或 built-in 方法调用'特殊方法'的时候, 29 详见 '对特殊方法的访问 - Special method lookup' 一文.
http://www.cnblogs.com/zzyzz/p/7743687.html 30 31 object.__setattr__(self, name, value) 32 当试图设置 attributes 的时候 __setattr__ 将被调用(instances.attribute = value), 33 从而代替 normal mechanism - __dict__[variables] = value 34 当 __setattr__ 要为一个 instance 的名字为 name 的 attribute 设置成值为 value 的时候, 35 实际上应该保证调用的是基类的 __setattr__ 方法, object.__setattr__(self, name, value). 36 37 object.__delattr__(self, name) 38 跟 __setattr__ 像类似, __delattr__ 用在删除 instances.attribute 的时候. 39 del instances.attribute 40 41 object.__dir__(self) 42 当对一个对象调用 dir(object) 方法的时候 __dir__ 被调用. 43 返回值是一个被 list 化, 并 sort 的序列. 44 45 Summarize, 46 其实 Customizing attribute access 跟 descriptor 关系紧密, 是描述符协议的前提, 47 可以将两者放在一起学习. 48 49 Reference, 50 Customizing attribute access 51 https://docs.python.org/3/reference/datamodel.html#customizing-attribute-access 52 53 descriptors 54 https://docs.python.org/3/reference/datamodel.html#descriptors