python 魔法方法连载三 __setattr()__

2020-04-14 17:47:44 浏览数 (1)

前言

上一篇我们讲到了当实例对象获取一个不存在的属性时,只要你重载了__getattr()__,就能定制错误提示。有了__getattr__(), 那必须有 __setattr__(),这篇我们就来聊下 __setattr__() 魔法方法。

__setattr__()

__setattr__(self,key,value) 当一个属性被设置时的行为 在类实例的每个属性进行赋值时,都会首先调用__setattr__()方法,并在__setattr__()方法中将属性名和属性值添加到类实例的__dict__属性中。

代码语言:javascript复制
>>> class Animal():
...     def __init__(self,name,age):
...             print(self.__dict__)
...             self.name = name
...             print(self.__dict__)
...             self.age = age
...             print(self.__dict__)
...
>>> dog = Animal('kitty',20)
{}
{'name': 'kitty'}
{'name': 'kitty', 'age': 20}

上面的示例中, 我们虽然没有重载__setattr__()方法,但是我们能看的出在调用__init__()方法对属性赋值时__dict__中依次插key 和 value。 下面的示例将重载__setattr__(),来动态的演示实例属性赋值时__dict__的变化。

代码语言:javascript复制
>>> class Animal():
...     def __init__(self,name,age):
...             self.name = name
...             self.age = age
...     def __setattr__(self,key,value):
...             print('-'*30)
...             print('setting:{},with:{}'.format(key,vaule))
...             print("current __dict__: {}".format(self.__dict__))
...             self.__dict__[key] = value
...
>>> dog = Animal('kitty', 20)
------------------------------
setting:name,with:kitty
current __dict__: {}
------------------------------
setting:age,with:20
current __dict__: {'name': 'kitty'}

可以看出,__init__()中两个属性赋值时,每次都会调用一次__setattr__()方法,__dict__也是从无到有。__setattr__ 负责在__dict__中对属性进行注册,所以 self.__dict__[key] = value 必不可少,大家可以试下,如果没有这句话,会报什么错?

0 人点赞