在装饰者之前和之后写

Nik*_*war 2 python decorator

我有以下示例代码,

def say_hello(f):
    def wrap():
        print "Hello"
    return wrap

def say_bye(f):
    def wrap():
        print "Bye"
    return wrap

@say_hello
@say_bye
def process():
    return "Processing"

process()
Run Code Online (Sandbox Code Playgroud)

输出:

Hello
Run Code Online (Sandbox Code Playgroud)

我期待输出为:

Bye
Hello
Processing
Run Code Online (Sandbox Code Playgroud)
  1. 可能有什么不对?
  2. 如何在函数调用之前和之后调用那些将被调用的装饰器?

手段,上面的例子,我可以有输出:

    Hello
    Processing
    Bye 
Run Code Online (Sandbox Code Playgroud)

use*_*ica 5

从装饰器返回的"wrap"函数实际上并没有调用它们应该包装的函数.这是一个问题,因为在调用包装函数之前不会调用从装饰器返回的函数.它取代了它的包装功能.以下装饰器语法:

@some_decorator
def func(arg):
    function_body()
Run Code Online (Sandbox Code Playgroud)

是以下代码的语法糖:

def func(arg):
    function_body()
func = some_decorator(func)
Run Code Online (Sandbox Code Playgroud)

因此,你想要的是

def say_hello(f):
    def wrap(*args, **kwargs):
        print "Hello"
        return f(*args, **kwargs)
    return wrap

def say_bye(f):
    def wrap(*args, **kwargs):
        return_value = f(*args, **kwargs)
        print "Bye"
        return return_value
    return wrap

@say_hello
@say_bye
def process():
    return "Processing"
Run Code Online (Sandbox Code Playgroud)

这将产生

Hello
Processing
Bye
Run Code Online (Sandbox Code Playgroud)