闭包:闭是封闭(函数内部嵌套函数),包是包含,闭包是指该内部函数对外部作用域而非全局作用域的变量的引用。
def func(x):
print(x)
func(1)
1
def outter(x):
x = 2
def inner():
print(x)
return inner
f = outter(1)
f()
2
意义:返回的函数对象,不仅仅是一个函数对象,在该函数外还包裹了一层作用域,这使得该函数无论在何处调用,优先使用自己外层包裹的作用域。
应用领域:延迟计算(原来是传参,现在是包起来)、爬虫领域。
def f1(url):#f1闭包函数
def spider():
print(url)
return spider#函数对象
taobao = spider('https://www.taobao.com')
taobao()
所谓装饰器就是用一个函数给另一个函数加功能而且不动原函数的代码,不改变原函数的调用方式。
import time
def index():
"""被装饰的函数"""
print('index')
time.sleep(1)
#为index增加计时功能
def time_coount(func):
"""装饰器"""
def f1():
start = time.time()
func()
end = time.time()
print(end-start)
return f1
index = time_coount(index)#这里第二个index是原来的index,但是第一个index已经不是原来的index,而是进过装饰之后的index
index()
import time
def index():
"""被装饰的函数"""
print('index')
time.sleep(1)
return 10
#为index增加计时功能
def time_coount(func):
"""装饰器"""
def f1():
start = time.time()
res = func()#如果原函数有返回值只需要将其赋给一个变量,然后将其在最内层返回
end = time.time()
print(end-start)
return res
return f1
index = time_coount(index)
print(index())
index
1.0000016689300537
10
import time
def index(x,y,z = 10):
"""被装饰的函数"""
print('index')
print(x,y,z)
time.sleep(1)
return 10
#为index增加计时功能
def time_coount(func):
"""装饰器"""
def wrapper(*args,**kwargs):#不论被装饰函数有没有参数都可以这样写
start = time.time()
res = func(*args,**kwargs)
end = time.time()
print(end-start)
return res
return wrapper
index = time_coount(index)
index(10,20,30)
index
10 20 30
1.0003015995025635
import time
#为index增加计时功能
username_list = []
def time_coount(func):
def wrapper(*args,**kwargs):
if username_list:
print('已经登录,请勿重复登录')
start = time.time()
res = func(*args, **kwargs)
end = time.time()
print(end - start)
return res
else:
username_inp = input('请输入用户名:')
pwd_inp = input('请输入密码:')
with open('user_info.txt','r',encoding='utf-8') as fr:
for user_info in fr:
username,pwd = user_info.strip().split(':')
if username_inp == username and pwd_inp == pwd:
print('登陆成功')
username_list.append(username_inp)
start = time.time()
res = func(*args, **kwargs)
end = time.time()
print(end - start)
return res
else:
print('登陆失败')
return wrapper
@time_count
def index(x,y,z = 10):
"""被装饰的函数"""
print('index')
print(x,y,z)
time.sleep(1)
return 10
#index = time_coount(index)
index(10,20,30)
功能:给双层装饰器加参数
在原来的要求上增加功能,需要判断用户动态的获取用户密码的方式,如果是file
类型的,我们则让用户进行认证。
import time
#为index增加计时功能
username_list = []
def auth(engine):
def time_count(func):
def wrapper(*args,**kwargs):
if engine == 'file':
if username_list:
print('已经登录,请勿重复登录')
start = time.time()
res = func(*args, **kwargs)
end = time.time()
print(end - start)
return res
else:
username_inp = input('请输入用户名:')
pwd_inp = input('请输入密码:')
with open('user_info.txt','r',encoding='utf-8') as fr:
for user_info in fr:
username,pwd = user_info.strip().split(':')
if username_inp == username and pwd_inp == pwd:
print('登陆成功')
username_list.append(username_inp)
start = time.time()
res = func(*args, **kwargs)
end = time.time()
print(end - start)
return res
else:
print('登陆失败')
else:
print('非法登录')
return wrapper
return time_count
@auth('file')
def index(x,y,z = 10):
"""被装饰的函数"""
print('index')
print(x,y,z)
time.sleep(1)
return 10
#time_count = auth('file')
#index = time_count(index)
index(10,20,30)
请输入用户名:xiaozhu
请输入密码:12306
登陆成功
index
10 20 30
1.000612497329712
在被装饰函数正上方,并且单独一行@装饰器名
def deco(func):
def wrapper(*args,**kwargs):
"""加功能区域"""
res = func(*args,**kwargs)
return res
return wrapper
原文:https://www.cnblogs.com/ghylpb/p/11574536.html