i meet this code today, and it seems confusing
class ClassOne:
def __init__(self,some_object):
self.not_important_attribute=some_object
class ClassTwo:
def __init__(self,some_object):
self.tmp=ClassOne(some_object)
def __getattr__(self,attr):
return getattr(self.tmp,attr)
a=ClassTwo('not_important_string')
print(getattr(a,'undefined_attribute',3))
When we use getattr at the last line we trigger the __getattr__ method in the SubClass , then delegate to the getattr(self.tmp,attr) function which will raise an exception if the attribute is undefined and no default value was given. But how the value 3 at the last line still go through all the process, and eventually return to getattr(a,'undefined_attribute',3) function ?. Because we didn't have a slot for the default value when we delegate getattr(self.tmp,attr), how is that possible ?
In your case
getattr(self.tmp,attr)
raises AttributeError and if getattr has third argument(default value) then it return default value instead of raising AttributeError
Step by step why 3 value is shown:
the super class has has an atribute
not_important_attributeand it is set when the constructor is called
class ClassOne:
def __init__(self,some_object):
self.not_important_attribute=some_object
Here, in the
ClassTwocontructor, you create an instance ofClassOneand save it intotmpvariable. Meaning that when you overrides__getattr__you will be asking for the value of attribute ofClassOne
print(getattr(a,'not_important_attribute',3))
not_important_string # founds the method
print(getattr(a,'any',3))
3 #doesn't found method, returns default
That is the same of directly do:
b = ClassOne("not_important_string")
print(getattr(b,'not_important_attribute',3))
not_important_string # founds the method
print(getattr(b,'any',3))
3 # doesn't found method, returns default
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With