首先解释下什么叫装饰器,所谓装饰器本质是一个python函数,可以在其他函数调用该函数的时候,不修改原代码而添加新的功能,减少代码的复用率,装饰器的返回值也是一个函数对象。
总结就是:不修改被装饰函数的调用方式、不修改被调用函数的源代码
前提了解:
全局作用域:定义的文件级别的变量、函数名,在全局不能访问到局部的变量
局部作用域:定义在函数的内部 ,在局部能访问全局的变量,不能修改全局定义的变量
全局变量适用于当前文件中所有方法的调用,若要修改全局变量,要在全局修改。若函数内部未查找到变量,会去全局变量中查找,若都不存在,会报错。
举例:
a = 1
def test():
a = 10 /*存在局部变量,取局部变量*/
print(a) /*a=10*/
test()
print(a) /*a=1*/
a = 1
def test():
# 没有局部变量,调用全局变量
print(a) /*a=1*/
test()
print(a) /*a=1*/
闭包函数定义:函数内部定义的函数,包含对外部作用域的引用(不是全局变量)
举例:
# 内部函数调用外部函数作用域变量
def outer():
x=1
def inner():
print(x)
inner()
outer()
装饰器:
无参装饰器 举例:
def old():
print('我是原来的代码')
def outer(func):
def inner():
func()
print('我是装饰器代码,这里写新功能')
return inner
old = outer(old) # 也可以写成 @outer
old()
有参装饰器 考虑在调用原函数的时候,有些要传参有些不需要的情况
def old():
print('我是原来的代码')
def outer(func):
def inner(*args, **kwargs): #主要是这里参数的修改
desc = func(*args, **kwargs) # 接收原函数的返回值
print('我是装饰器代码,这里写新功能')
return desc
return inner
old = outer(old) # 也可以写成 @outer 使用装饰器
old()
若存在一个函数被多个装饰器装饰,执行顺序是按照从上往下执行的
类装饰器 顾名思义就是装饰的方法是一个类,可以用于管理类自身,或者用来拦截实例创建调用以管理实例。
举例:类装饰函数
class Test:
def __init__(self, func):
print('test init')
# 打印出调用装饰器的函数
print('func name is %s ' % func.__name__)
self.func = func
# 调用方法
def __call__(self, *args, **kwargs):
print('装饰器中的功能')
#调用的函数需要传参数时
self.func(*args, **kwargs)
@Test
def aa(name, age):
print('final',name ,age)
aa('tom',10)
运行结果: