[PYTHON] Implement a model with state and behavior (3) --Example of implementation by decorator

Last time (Implement a model with states and behaviors (2)), we implemented StopWatch with three states in two ways. .. This time, implement StopWatch using * decorator *.

First, describe the state transition with * decorator *. It becomes easy to understand whether it is a method that transitions to a state.

from enum import auto


def transit(state):
    def decorator(func):
        def inner(self, *args, **kwargs):
            self.start_stop, self.reset = self._TRANSIT[state]
            func(self, *args, **kwargs)
        return inner
    return decorator


class StopWatch:
    WAIT, PAUSE, MEASURE = auto(), auto(), auto()

    def __init__(self):
        self._TRANSIT = {StopWatch.WAIT: (self.start, lambda *args: None),
                         StopWatch.PAUSE: (self.start, self.reset_time),
                         StopWatch.MEASURE: (self.pause, lambda *args: None)}
        self._TRANSIT_REVERSED = {v: k for k, v in self._TRANSIT.items()}
        self.start_stop, self.reset = self._TRANSIT[StopWatch.WAIT]

    @property
    def state(self):
        return self._TRANSIT_REVERSED[self.start_stop, self.reset]

    @transit(MEASURE)
    def start(self):
        pass

    @transit(PAUSE)
    def pause(self):
        pass

    @transit(WAIT)
    def reset_time(self):
        pass

Furthermore, try cutting out the state transition table with a decorator. The behavior decorator represents the behavior in a certain state.

from enum import auto
from state_machine import behavior, transit


class StopWatch:
    WAIT, MEASURE, PAUSE = auto(), auto(), auto()

    def __init__(self):
        self.state = StopWatch.WAIT

    @behavior(WAIT, "start")
    @behavior(MEASURE, "pause")
    @behavior(PAUSE, "start")
    def start_stop(self):
        pass

    @behavior(PAUSE, "reset_time")
    def reset(self):
        pass

    @transit(MEASURE)
    def start(self):
        pass

    @transit(PAUSE)
    def pause(self):
        pass

    @transit(WAIT)
    def reset_time(self):
        pass

state_machine.py


from functools import wraps


def transit(state):
    def decorator(func):
        @wraps(func)
        def inner(self, *args, **kwargs):
            self.state = state
            func(self, *args, **kwargs)
        return inner
    return decorator


def behavior(state, function):
    def decorator(func):
        @wraps(func)
        def inner(self, *args, **kwargs):
            if self.state == state:
                getattr(self, function)(*args, **kwargs)
            else:
                func(self, *args, **kwargs)
        return inner
    return decorator

It is assumed that the state is kept in self.state, but since the same * decorator * can be used in other models, it was cut out as a module state_machine.

At the timing of processing the decorator, the function is still unbound, so the behavior is given as a string. You can also use the function __name__ to call a bound method at runtime. (Only applicable parts are shown below.) Note that if you have * decorator * that doesn't use functools.wrap (), it won't work as expected. (* decorator * doesn't rewrite the function __name__ when usingfunctools.wrap ().)

state_machine.py


def behavior(state, function):
...
            if self.state == state:
                getattr(self, function.__name__)(*args, **kwargs)
...
...
    @behavior(PAUSE, reset_time)
    def reset(self):
        pass
...

Recommended Posts

Implement a model with state and behavior (3) --Example of implementation by decorator
Implement a model with state and behavior
Implement the mathematical model "SIR model" of infectious diseases with OpenModelica (example of repeating regulation and deregulation)
Let's make a nervous breakdown application with Vue.js and Django-Rest-Framework [Part 3] ~ Implementation of nervous breakdown ~
Transfer function / state space model of RLC series circuit and simulation by Python
Implementation of TRIE tree with Python and LOUDS
Implementation of a model that predicts the exchange rate (dollar-yen rate) by machine learning
Implement a discrete-time logistic regression model with stan
Example of reading and writing CSV with Python
Transfer function / state space model of spring / mass / damper system and simulation by Python
I implemented "Basics of Time Series Analysis and State Space Model" (Hayamoto) with pystan
[Python] Implementation of clustering using a mixed Gaussian model
[# 2] Make Minecraft with Python. ~ Model drawing and player implementation ~
Create a batch of images and inflate with ImageDataGenerator
Create a 3D model viewer with PyQt5 and PyQtGraph
Learning model creation, learning and reasoning
Memorandum of saving and loading model
Regression model and its visualization using scikit-learn
Loading and testing Chainer's trained imagenet model
Implement a model with state and behavior
Decorate with a decorator
A story of reading a picture book by synthesizing voice with COTOHA API and Cloud Vision API
Implementation example of centrally managing inventory and variables by linking Ansible and serverspec (supports multiple servers)
Implementation of VGG16 using Keras created without using a trained model
Save the output of GAN one by one ~ With the implementation of GAN by PyTorch ~
Reuse the behavior of the @property method by using a descriptor [16/100]
Implement the mathematical model "SIR model" of infectious diseases with OpenModelica
Detect objects of a specific color and size with Python
Analyze the topic model of becoming a novelist with GensimPy3
Explanation of CSV and implementation example in each programming language
Time series analysis using a general Gaussian state-space model using Python [Implementation example considering exogenous and seasonality]
Find the white Christmas rate by prefecture with Python and map it to a map of Japan
A story and its implementation that arbitrary a1 * a2 data can be represented by a 3-layer ReLU neural network with a1 and a2 intermediate neurons with an error of 0.
Explanation and implementation of SocialFoceModel
Easily cProfile with a decorator
Environment construction of Tensorflow and Chainer by Window with CUDA (with GPU)
Miyashita's example of analytical mechanics, solved exercises and moved with animation
Crawling with Python and Twitter API 2-Implementation of user search function
[Required subject DI] Implement and understand the mechanism of DI with Go
[Python] Implementation of Nelder–Mead method and saving of GIF images by matplotlib
Try to make a blackjack strategy by reinforcement learning ((1) Implementation of blackjack)
Implementation example of hostile generation network (GAN) by keras [For beginners]
Define a custom argument type with click (Example: Implementation of a type that makes a string eval an optional value)
Building a distributed environment with the Raspberry PI series (Part 1: Summary of availability of diskless clients by model)