0

Say I wanted to alter an instance variable after running each method in a class. What is the best way to do this? I am aware of how to use decorators (at a very basic level), but don't know how to modify instance variables from a class using them.

As an example, I want to achieve what is shown below, but without explicitly calling post_method_routine from each method

class MyClass():
    def __init__(self):
        self.state = True

    def post_method_routine(self):
        self.state = False
        print(self.state)

    def method1(self):
        # do stuff
        self.post_method_routine()

    def method2(self):
        # do stuff
        self.post_method_routine()

    def methodN(self):
        # do stuff
        self.post_method_routine()

myinst = MyClass()
myinst.method1() # Output: False

1 Answer 1

5

decorators are a clean way to solve this

def post_method(fn):
    def __inner(self,*args,**kwargs):
        result = fn(*args,**kwargs)
        self.post_method_routine()
        return result
    return __inner

now just use that ... but i dont know what your really accomplishing by doing this

class MyClass():
    def __init__(self):
        self.state = True

    def post_method_routine(self):
        self.state = False
        print(self.state)

    @post_method
    def method1(self):
        # do stuff

    @post_method    
    def method2(self):
        # do stuff

if you wanted to automagically apply it to all methods that start with method you could do

class MyClass():
    def __init__(self):
        self.state = True

    def post_method_routine(self):
        self.state = False

    def method1(self):
        # do stuff

    def method2(self):
        # do stuff

for method_name in dir(MyClass):
    if method_name.startswith("method"):
        setattr(MyClass,method_name,post_method(getattr(MyClass,method_name)))

however i would strongly discourage doing this as it appears to be "magic" to the casual observer

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.