简体   繁体   中英

Decorator Functions in Python

The Decorator Function of Python has this simple template

@A

@B

def C():

It modify the C function to C=A(B(C));

Let's give a more specific example

@request("POST", "%(channel)d/sequence/%(args)s") 
@response("%d")

    def outputSequence(self, channel, args):
        self.checkDigitalChannelExported(channel)
        self.checkPostingValueAllowed()
        self.checkDigitalChannel(channel)
        (period, sequence) = args.split(",")
        period = int(period)
        GPIO.outputSequence(channel, period, sequence)
        return int(sequence[-1])

So from the above, would the transformed function be

like request(response(outSequence(self, channel, args))?

Parameterized decorators behave a bit differently. The function request accepts only the arguments, it's a decorator maker :

def request(arg1, arg2):
    def my_decorator(func):
        def wrapper():
           #do something
        return wrapper
    return my_decorator

So the function calls is like:

decorator = request(arg1, arg2)
response_decorator = decorator(response(arg1, arg2))
outputSequence = response_decorator(outputSequence(self, arg1, arg2))

Here's a tiny example:

>>> def make_decorators(arg1, arg2):
        def decorator(func):
            def wrapper():
                print("We got here!")
            return wrapper
        return decorator

>>> @make_decorators(1, 2)
    def my_func():
        pass


>>> my_func()
We got here!

Close. When a decorator is given one or more arguments, the effect is to call the decorator, which returns a function that is then applied to the function it is decorating. The effect is something more like (as Niklas B. pointed out):

request("POST", "%(channel)d/sequence/%(args)s")(
   response("%d")(
       outputSequence))(self, channel, args)

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