一、闭包是什么?
在实现装饰器之前,我们需要了解闭包。闭包,为函数创建一块区域(内部变量供自己使用),为他以后执行提供数据。
直接上代码:
def wrapper()
def inner():
print(1)
return inner
w = wrapper()
print(w)
w()
-----------------------------
<function wrapper.<locals>.inner at 0x000001E3E1F28160>
1
这段代码定义了一个wrapper函数,返回一个inner函数的内存地址。即w
表示inner函数的内存地址,当我们w()
则调用inner函数,即打印了1
下面看一段代码,判断输出值是多少?
name = 'Jack'
def Foo(name):
def wrapper():
print(name)
return wrapper
v = Foo('Captain')
v()
-----------------------
# 结果
Captain
执行原理
二、装饰器是什么
装饰器,顾名思义就是对某样东西进行装饰,其本质不便。如男生化妆,就算他化妆成了一个绝世美女,其本质还是男的。所以在python中的装饰器就是在函数执行前或执行后进行某些操作(添加某些功能)。
标准一点的说法:装饰器就是在不改变原函数的情况下对函数进行装饰(执行函数前后的代码操作)
语法格式
在调用的函数上面写@函数
def foo(func)
def inner
return func() # 这里的func可以理解为一个变量指向了bar函数
return inner
@foo
def bar()
pass
@foo
的执行流程
- 第一步:执行foo函数并将下面的函数(bar)进行参数传递,相当于:foo(bar)
- 第二步:将foo的返回值重新赋值给下面的函数名。 bar= foo(bar) <= inner ,这里将inner函数的内存地址复制给bar
三、如何实现装饰器
def foo(func):
def inner():
print('这是foo函数中的inner函数')
return func()
return inner
@foo
def index():
print('这是index函数')
index()
-----------------------------
>>> 这是foo函数中的inner函数
>>> 这是index函数
通过上面的代码,发现原函数照常执行,不过在执行之前打印了inner函数的print语句,这样就可以实现在函数执行前做一些操作。
四、实现简单的用户认证
def wrapper(func):
def inner(*args, **kwargs):
if not kwargs['token']:
print('您需要先登录')
if not kwargs['token'] == 6666: # 这里也可以写成数据库查询操作
print('认证已失效,请重新登录')
else:
f = func(*args, **kwargs)
return f
return inner
@wrapper
def order(token):
print('这是用户订单')
v = order(token=6666)