简体   繁体   中英

Python: Create class whose constructor accepts a user-given function which becomes a method

Is it possible in python (3) to have a class whose constructor takes as an argument a function which is then converted into a method on that instance?

I want to do something like:

class Example:
    def __init__(self, val1, val2, user_passed_function):
        self.val1 = val1
        self.val2 = val2
        # this next line doesn't quite get what I'm going for...
        self.upf = user_passed_function

    def user_function_doer(self, *args, **kwargs):
        # THIS LINE IS KEY
        return self.upf(*args, **kwargs)

def upf1(instance, arg):
    return instance.val1 + arg

def upf2(instance, arg):
    return instance.val2 + arg

and then have the following:

ex1 = Example(1, 2, upf1)
ex1.user_function_doer(10)
## should return 1 + 10 = 11

ex2 = Example(1, 2, upf2)
ex2.user_function_doer(10)
## should return 2 + 10 = 12

My actual use case is a bit more complicated than this, but basically I want to be able to pass a function at instantiation time that, later on, will have the ability to access attributes on the instance.

Possible?

I believe if I change the line after the # THIS LINE IS KEY comment to read:

    def user_function_doer(self, *args, **kwargs):
        # THIS LINE IS KEY
        return self.upf(self, *args, **kwargs)

things might work out ok. But it feels odd to need to write the self argument explicitly there...for actual instance methods it would be passed automatically. Is there a way to get that to happen?

You have mentioned an instance argument in the definition of upf1 and upf2
but do not pass self in return self.upf(*args, **kwargs)

return self.upf(self,*args, **kwargs) solves that and seems to work as expected

Also... you are missing the self in def user_function_doer(self,*args, **kwargs):

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM