python __getattr__ __getattribute__

setattr(x,y,z)   ----> x.y=z

setattr(Test,'x'.1)    Test 为类对象

getattr(object,name[,default])

getattr(x,'y')   -----> x.y

不会触发__getattribute__ 

 

__getattr__:

如果实例instance通过instance.name访问属性name,

如果类中没有定义name,会触发此方法,

类中定义了name 这个属性,不会触发此方法

注意:如果在__getattr__(self, attr)存在通过self.attr访问属性,会出现无限递归错误。

 

__getattribute__

如果实例instance通过instance.name访问属性name,

不管类中有没有定义name 属性,都会触发此方法,

 

注意:如果在__getattribute__(self, attr)方法下存在通过self.attr访问属性,会出现无限递归错误

如果类中定义了__getattr__方法,除非通过__getattribute__显式的调用它,或者__getattribute__方法出现AttributeError错误,否则__getattr__方法不会被调用

  • test.x =1 
  • print(test.x)      设置/访问属性 每次都会调用 __getattribute__方法

 

test.x =1  ---->调用__setattr__,不建议自己实现

print(test.x)  ====> 如果x属性没有设置__getattribute__会去调用 __getattr__方法

 

class Test1:
    def __init__(self):
        self.s = 2

    def __getattr__(self, key):
        print("__getattr___", key)
        if key == 'x':
            return 'default x'
        return key

 T = Test1()
    print(T.s) 
    #输出 
    # 2
    print(T.f)  #类没有f属性,就调用了__getattr__
    #输出
    #__getattr___ f
    #f
class Test3():
    def __init__(self):
        self.s = 2

    def __getattribute__(self, key):
        print('__getattribute__')
        if key == 'x':
            return 'default x'
        else:
            return key
----------------------
    T =Test3()  #不管类里有没有该属性 都调用了__getattribute__
    print(T.s)
    #输出:
    #__getattribute__
    #s
    print(T.x)
    # 输出
    # __getattribute__
    # default
    # x
class Test2:
    def __init__(self):
        self.s = 2

    def __getattribute__(self, key):
        print('__getattribute__')
        if key == 'x':
            pass
            # return 'default x'
        else:
            raise AttributeError

    def __getattr__(self, key):
        print("__getattr___", key)

        return key
--------------------------------
    T = Test2()
    #输出
    # print(T.x)
    #__getattribute__
    #None

    print(T.f) # __getattribute__ 抛出AttributeError,调用 __getattr___
    #输出
    # __getattribute__
    # __getattr___ f
    # f

 

posted @ 2019-10-27 20:45  周零开  阅读(15)  评论(0)    收藏  举报