天天看点

python装饰器带括号和不带括号的语法和用法

装饰器的写法补充:

通常装饰器的写法是@func(),而有的时候为了减少出错率,可能会写成@func,没有()括号,这时我们可以这样定义,来减少括号。下面通过两个例子还看。

一般装饰器的写法:
1 def log(func=None):
 2     
 3     def inner(*args, **kwargs):
 4         print('do something before')
 5         res = func(*args, **kwargs)
 6         print('do something after')
 7         return rees
 8     
 9     return inner
10 
11 #使用装饰器
12 @log()
13 def my_func():
14     print('i am my_func')
15 
16 #运行这个函数
17 my_func()      

运行结果:

1 do something before
2 i am my_func
3 do something after      
可以不带括号的装饰器写法

需要增加判断在函数内,用于判断使用装饰器的函数是否可以调用,以达到括号的***写法

判断的装饰器写法

def log(func=None):
    
    #需要再次嵌套一层装饰器,才可以供下面运行时使用
    def wrapper(fun)
        def inner(*args, **kwargs):
            print('do something before')
            res = fun(*args, **kwargs)
            print('do something after')
            return rees
        
        return inner
    
    #判断func(参数):
    if func is None:
        return wrapper
        
    #如果func是可以调用的函数    
    elif callable(func):
        return wrapper(func)
    

#使用装饰器的时候,两种写法都可以运行

第一种不带括号:
@log
def my_func():
    print('i am my_func')

第二种带括号的:
@log()
def my_func():
    print('i am my_func')


#运行这个函数
my_func()      

不带括号的理解:

@log =>等同于 my_func = log(my_func)      

带括号的理解:

@log() =>等同于 my_func = log()(my_func)      

两种方式的一样,运行结果:

1 do something before
2 i am my_func
3 do something after      

结论: 内嵌之后,可以增加判断条件,增加了装饰器的灵活性。