Skip to main content
 首页 » 编程设计

python之双装饰器,为什么我的封闭函数之一没有执行

2025年05月04日21zhenyulu

我试图通过以下代码了解如何在一个函数上使用两个装饰器:

def fxn(func): 
    print("fxn_outer 1") 
    def fxn_inner(*args, **kwargs): 
        print("fxn_inner 1") 
    return fxn_inner 
 
def fxn2(func): 
    print("fxn_outer 2") 
    def fxn_inner2(*args, **kwargs): 
        print("fxn_inner 2") 
    return fxn_inner2 
 
@fxn 
@fxn2 
def fxn3 (a, b): 
    print(a + b) 
 
fxn3(1, 2) 

我很困惑为什么在上面的代码中执行了fxn_inner,而fxn_inner2却没有。

输出是:

fxn_outer 2 
fxn_outer 1 
fxn_inner 1 

当我期望以下输出时:

fxn_outer 2 
fxn_outer 1 
fxn_inner 1 
fxn_inner 2 

为什么当我同时调用两个包装函数时只执行其中一个?

请您参考如下方法:

装饰器只是调用函数和重新分配名称的语法糖,所以你所做的等同于:

fxn3 = fxn2(fxn3) 
fxn3 = fxn(fxn3) 
 
fxn3(1, 2) 

那么发生了什么?第一次赋值后,你有 fxn3 == fxn2_inner。 在第二行之后你有 fxn3 == fxn_inner。

但是fxn(和fxn_inner)的定义他们只是丢掉了参数func!因此,当您调用 fxn3(1,2) == fxn_inner(1, 2) 时,您看不到它被调用。

如果你想调用原始函数,你应该在 *_inner 函数中调用 func:

def fxn(func): 
    print("fxn_outer 1") 
    def fxn_inner(*args, **kwargs): 
        print("fxn_inner 1") 
        return func(*args, **kwargs) 
    return fxn_inner 
 
def fxn2(func): 
    print("fxn_outer 2") 
    def fxn_inner2(*args, **kwargs): 
        print("fxn_inner 2") 
        return func(*args, **kwargs) 
    return fxn_inner2