闭包:
如何定义一个闭包?
闭包函数必须有内嵌函数
内嵌函数必须要引用外层函数的变量
闭包函数返回内嵌函数的地址(函数名称)
作用:
在不修改源码 的情况下增加功能
创建一个闭包函数:
def func():
name = 'zs'
def inner():
print(name)
return inner
f = func()
f()
#zs
判断闭包函数的方法:__closure__
def func():
name = 'ls'
def inner():
print(name)
print(inner.__closure__)#如果是闭包,会打印出<cell:...> 如果不是,则打印None
return inner
f = func()
f()
#(<cell at 0x00000000039BF2E8: str object at 0x0000000002994998>,)
#ls
name = 'ls'
def func():
def inner():
print(name)
print(inner.__closure__)
return inner
f = func()
f()
#None
#ls
#因为引用的是外部变量不是外部函数的变量所有不是闭包
创建一个计算函数执行花费时间的闭包函数
import time
#功能函数
def fun():
print('哈哈哈')
#闭包函数
def timer(func):
def inner():
start = time.time()
time.sleep(0.01)
func()#执行fun()函数
end = time.time()
print(end-start)
return inner
fun = timer(fun)
fun()
装饰器:
装饰器的本质:
一个闭包函数
装饰器的作用:
在不修改原函数及其调用的情况下对原函数功能进行扩展
语法糖:
格式:@装饰器名称
可以理解成装饰器就时将一个闭包函数使用语法糖的形式放在需要使用装饰器的函数上
注意:装饰器函数需要写在功能函数的上面,因为代码是从上往下执行写在下面找不到
使用语法糖创建一个计算函数执行花费的时间
import time
def timer(func):
def inner():
start = time.time()
time.sleep(0.01)
func()#执行fun()函数
end = time.time()
print(end-start)
return inner
@timer #语法糖:等价于fun=timer(fun)
def fun():
print('哈哈哈')
fun()
创建一个带返回值的装饰器
import time
def timer(func):
def inner():
start = time.time()
time.sleep(0.01)
#2.接受返回值
ret = func()
end = time.time()
print(end-start)
#3.返回返回值
return ret
return inner
@timer
def fun():
print('哈哈哈')
#1.设置返回值
return '嘿嘿嘿'
ret = fun()
print(ret)
创建一个带参数的装饰器
import time
def timer(func):
#1.传递参数
def inner(s):
start = time.time()
time.sleep(0.01)
#2.传递参数
func(s)
end = time.time()
print(end-start)
return inner
@timer
def fun(s):
print('哈哈哈',s)
fun('嘿嘿')
定义一个可以传递任意参数的装饰器
import time
def timer(func):
def inner(*args,**kwargs):
start = time.time()
time.sleep(0.01)
func(*args,**kwargs)
end = time.time()
print(end-start)
return inner
@timer
def fun(*args,**kwargs):
print(args,kwargs)
fun('嘿嘿','哈哈','呵呵',name='张三')
多个装饰器的使用:
可以使用多个装饰器装饰同一个函数,离函数近的先装饰
def fun1(func):
def inner1():
return '《'+func()+'》'
return inner1
def fun2(func):
def inner2():
return '*'+func()+'*'
return inner2
@fun2
@fun1
def bookName():
return '大话西游'
print(bookName())
#*《大话西游》*