Python进阶-III 函数装饰器(Wrapper)

1、引入场景:

检查代码的运行时间
import time

def func():
    start = time.time()
    time.sleep(0.12)
    print('看看我运行了多长时间!')
    end = time.time()
    print('此段代码运行时长为:%s'%(end - start))

func()
如果有大量的函数要检查,这样加入代码太费功夫!考虑提取为一个函数,要检查时直接调用即可
def check_time(f):
    start = time.time()
    time.sleep(0.12)
    f()
    end = time.time()
    print('此段代码运行时长为:%s' % (end - start))

check_time(func)
还是有问题,有人嫌每次都去调用该函数很麻烦!
能不能,在不修改要测试远行时长的函数的调用方式前提下,还想在原来的函数前后添加测试时长功能?
def timing(f):  # 装饰器函数
    def inner():
        start = time.time()
        time.sleep(0.12)
        f()  # 被装饰函数
        end = time.time()
        print('此段代码运行时长为:%s' % (end - start))

    return inner

func = timing(func)
func()

这里就可以定义装饰器函数了,用来装饰其他函数,添加相关功能的函数叫装饰器函数

2、语法糖的使用

@timing  # @装饰器函数名 相当于前面函数调用前的赋值:func_to = timing(func_to)
def func_to():  # 被装饰的函数
    a = 1000000
    b = 1223434
    return a * b

func_to()

3、装饰器的作用

  不想修改函数的调用方式 但是还想在原来的函数前后添加功能

上面的例子中timmer就是一个装饰器函数,只是对一个函数 有一些装饰作用

 

4、装饰带参数的函数

def timing_arg(f):
    def inner(a):
        start = time.time()
        re = f(a)
        end = time.time()
        print('此段代码运行时长为:%s' % (end - start))
        return re

    return inner


@timing_arg
def func_have_arg(a):
    result = a * 10000000
    return result

5、装饰带可变参数的函数

 1 def wrapper(f):  # 装饰器函数,f是被装饰的函数
 2     def inner(*args, **kwargs):
 3         '''在被装饰函数之前要做的事'''
 4         ret = f(*args, **kwargs)  # 被装饰的函数
 5         '''在被装饰函数之后要做的事'''
 6         return ret
 7 
 8     return inner
 9 
10 @wrapper  # 语法糖 @装饰器函数名
11 def func_101(a, b):  # 被装饰的函数
12     time.sleep(0.01)
13     print('老板好同事好大家好', a, b)
14     return '新年好'
15 
16 print(func_101(100, b=200))

6、编程原则: 开放封闭原则#
  开放 : 对扩展是开放的
  封闭 : 对修改是封闭的

posted @ 2019-11-26 19:19  四方游览  阅读(3564)  评论(1编辑  收藏  举报