[Road to Python Intermediate] Define __getattr__ function in class

Link to summary

https://qiita.com/ganariya/items/fb3f38c2f4a35d1ee2e8

Introduction

In order to study Python, I copied a swarm intelligence library called acopy.

In acopy, many interesting Python grammars and idioms are used, and it is summarized that it is convenient among them.

This time, let's define a __getattr__ special method in the class.

Instance attributes

As a way to retrieve attributes used inside an instance in Python There is a way to refer to __dict__.

The name of the namespace used inside the instance is defined as a dictionary in __dict __.

For example, take the following example.

class A:

    def __init__(self, x, y):
        self.x = x
        self.y = y


# {'x': 10, 'y': 20}
a = A(10, 20)
print(a.__dict__)

Instance a has names $ x, y $ You can retrieve them as a dictionary.

__getattr__

You can define a special method called __getattr__ in a Python class.

In a Python instance name call If called with an undefined name, it will return ** AttributeError **.

But if __getattr__ is defined, Instead of returning an AttributeError "on a call with an undefined name", __getattr__ is executed.

Let's look at an example.

class A:

    def __init__(self, x, y):
        self.x = x
        self.y = y

    def __getattr__(self, name):
        print(name, 'getattr')
        if name == 'hello':
            return self.world
        raise AttributeError

    def world(self, x):
        return x


'''
{'x': 10, 'y': 20}
hello getattr
<bound method A.world of <__main__.A object at 0x10e602150>>
hello getattr
20
'''
a = A(10, 20)
print(a.__dict__)
print(a.hello)
print(a.hello(20))

The __getattr__ method is defined in the A class above.

When I try to call ʻa.hello, the attribute hello is not defined in a. So the getattr` method is called and returns the world method instead.

In ʻa.hello (20)`, the world method is returned first, and the world method is given a value of 20 and executed. Therefore, it is executed when the name hello is confirmed.

Therefore, if you use the above properties, you will get the following useless code.

class A:

    def __init__(self, x, y):
        self.x = x
        self.y = y

    def __getattr__(self, name):
        print(name, 'getattr')
        if name == 'hello':
            return self.world
        if name == 'world':
            return self.great
        if name == 'great':
            return self.bad
        if name == 'bad':
            return 0
        raise AttributeError


'''
{'x': 10, 'y': 20}
hello getattr
world getattr
great getattr
bad getattr
0
'''
a = A(10, 20)
print(a.__dict__)
print(a.hello)

Application example

I can't think of many application examples, If there is no attribute, I think there is something like letting you do alternative rule processing. Also, it seems that the branch etc. may be changed depending on the call name.

class A:

    def __getattr__(self, name):
        self.nothing(name)

    def exist(self):
        print('exist!')

    def nothing(self, name):
        print(f'nothing {name}')


'''
exist!
nothing unnti
'''
a = A()
a.exist()
a.unnti

In addition, as each content as a separate article at a later date It seems that it can also be used by throwing an exception code when there is no name in the lambda expression.

References

-Python attribute handling mechanism

Recommended Posts

[Road to Python Intermediate] Define __getattr__ function in class
[Road to intermediate Python] Define in in your own class
[Road to Python Intermediate] Call a class instance like a function with __call__
A road to intermediate Python
[Python] Road to snake charmer (3) Python class
[Road to Intermediate] Understanding Python Properties
[Road to intermediate Python] Install packages in bulk with pip
[Road to intermediate Python] Use if statement in list comprehension
[Introduction to Python] How to use class in Python?
[Road to intermediate Python] Use ternary operators
How to dynamically define variables in Python
How to use __slots__ in Python class
[Road to intermediate Python] Use lambda expressions
[Road to intermediate Python] Article link summary
Automatically register function arguments to argparse in Python
To execute a Python enumerate function in JavaScript
[Road to Intermediate] Python seems to be all objects
case class in python
Class notation in Python
How to define Decorator and Decomaker in one function
Convert / return class object to JSON format in Python
[Road to intermediate level] Utilize Python's built-in function vars
Covector to think in function
Create a function in Python
To flush stdout in Python
Use callback function in Python
ntile (decile) function in python
Login to website in Python
Nonlinear function modeling in Python
Draw implicit function in python
Speech to speech in python [text to speech]
Immediate function in python (lie)
How to develop in Python
Post to Slack in Python
How to use the __call__ method in a Python class
How to define multiple variables in a python for statement
How to sample from any probability density function in Python
To return char * in a callback function using ctypes in Python
I tried to implement the mail sending function in Python
[Road to intermediate Python] Enables comparison operations with original classes
How to write a Python class
[Python] How to do PCA in Python
Implement R's power.prop.test function in python
Function argument type definition in python
Included notation in Python function arguments
Landmines hidden in Python class variables
How to collect images in Python
[Road to Python intermediate] Dynamically specify execution method by variable name
[Python 3.8 ~] How to define a recursive function smartly with a lambda expression
How to use SQLite in Python
Write AWS Lambda function in Python
Read PNG chunks in Python (class)
Measure function execution time in Python
In the python command python points to python3.8
Try to calculate Trace in Python
I wrote a function to load a Git extension script in Python
Road to Linux Intermediate: Network Edition
[Python3] Define a decorator to measure the execution time of a function
How to use Mysql in python
How to wrap C in Python
How to use ChemSpider in Python