闭包函数和装饰器
一-什么是闭包函数?
闭:封闭
包:包裹
比如手机的举例
1.闭包函数必须在函数内部定义
2.闭包函数可以引用外层函数的名字
-闭包函数是:函数的嵌套、函数的对象、名称空间和作用域 结合体。
****闭合函数是为了装饰器做准备
def func(y): x = 100 #inner 是一个闭包函数 def inner(): print(x) print(y) return inner inner = func(1) inner() >>>>>> 100 1
二、装饰器
-什么是装饰器?
装饰:装饰 ,修饰。
器:工具
********开放封闭***** 装饰器必须遵循“开放封闭“的原则
-开放:
对函数的功能添加是开放的;
-封闭:
对函数的功能修改是封闭的。
-装饰器的作用?
-在不修改被装饰对象的源代码和调用方式前提下,添加新的功能。
##装饰器的定义必须遵顼:
-不修改被装饰对象的源代码
-不修改被装饰对象的调用方式
-为什么要使用装饰器?
可以解决代码冗余问题,提高代码的可扩展性
-怎么使用装饰器?
-装饰器的应用:
-登录时间
-登录认证
-编写装饰器
通过闭包函数来实现装饰器
#爬虫的获取技术 import requests # 爬虫请求工具,外国大佬给我们提供的爬虫的第三方请求库 #方式一直接传参 def spider_func(url): #往url发送请求,获取相响应数据 response = requests.get(url) #必须接受url if response.status_code ==200: #状态码:200 print(len(response.text)) #获取当前的url中所有文本 print(response.text) url = 'https://fanyi.baidu.com/#en/zh/spider' spider_func(url) >>>>>>>>> 219724 ###len <!DOCTYPE html> ####文本 <html> <head> 用闭包函数的方法 def wrapper(url): def spider_func(): response = requests.get(url) if response.status_code == 200: print(len(response.text)) print(response.text) return spider_func #return 的位置一定要特别注意 url ='https://fanyi.baidu.com/#en/zh/spider' spider_baidu = wrapper(url) spider_baidu() >>>>>>>> # 功能: 统计下载电影的函数的运行时间 import time def downlode_moive(): print('开始下载电影......') #模拟下载电影 time.sleep(5)#等待3秒钟 print('电影下载成功......')#电影下载成功 return '千与千寻.mp4' start_time = time.time() #获取当前时间戳 downlode_moive() end_time = time.time()#获取当前时间戳 print(f'下载消耗的时间{end_time - start_time}')
# 功能: 统计下载电影的函数的运行时间 import time def download_movie(): print('开始下载电影......') #模拟下载电影 time.sleep(2)#等待3秒钟 print('电影下载成功......')#电影下载成功 return '千与千寻.mp4' # # start_time = time.time() #获取当前时间戳 # download_movie() # # end_time = time.time()#获取当前时间戳 # print(f'下载消耗的时间{end_time - start_time}') def download_record(func): def inner_movie(): start_time = time.time() res = func() end_time = time.time() print(f'消耗时间:{end_time - start_time}') return res return inner_movie download_movie = download_record(download_movie) download_movie() >>>>>>> 开始下载电影...... 电影下载成功...... 消耗时间:2.00022292137146 #####被接收对象接收2个参数 import time def download_movie(a,c): print(f'{a,c}电影开始下载......') time.sleep(2) print('电影下载完成......') return '太阳.mp4' def download_record(func): def inner_movie(a,c): # url = 'https://www.cnblogs.com/wangeraaa/p/10236180.html' start_time = time.time() res = func(a,c) end_time = time.time() print(f'下载时间:{end_time - start_time}') print(res) return inner_movie download_movie = download_record(download_movie) download_movie('avd',c = 'dfe') >>>>>>>> ('avd', 'dfe')电影开始下载...... 电影下载完成...... 下载时间:2.000197410583496 太阳.mp4 ####被装饰的对象接收多个参数 import time def download_movie(*arg,**kwargs): print(f'{*arg,kwargs}电影开始下载......') time.sleep(2) print('电影下载完成......') return '太阳.mp4' def download_record(func): def inner_movie(*arg, **kwargs ): # url = 'https://www.cnblogs.com/wangeraaa/p/10236180.html' start_time = time.time() res = func(*arg,**kwargs) end_time = time.time() print(f'下载时间:{end_time - start_time}') print(res) return inner_movie download_movie = download_record(download_movie) download_movie('avd','dfe',url = 'https://www.cnblogs.com/wangeraaa/p/10236180.html') >>>>>>>> C:\Users\86187\AppData\Local\Programs\Python\Python36\python.exe E:/PycharmProjects/study/11.8.py ('avd', 'dfe', {'url': 'https://www.cnblogs.com/wangeraaa/p/10236180.html'})电影开始下载...... 电影下载完成...... 下载时间:2.001342296600342 太阳.mp4
装饰器的完整最终模板
def func1():#####被装饰的对象 pass def wrapper(func): def inner(*arg, **kwargs): #让用户输入内容 username = input('请输入你的名字:') if username == 'tank': print('right') res = func(*arg, **kwargs) return res else: print('wrong') return inner func1 = wrapper(func1) func1()
魔法糖
''' 装饰器的语法糖,是属于装饰器的。 @: 装饰器的语法糖 # 注意: 在使用装饰器语法糖时,装饰器必须定义在被装饰对象之上。 ''' import time # 统计函数执行时间装饰器 def wrapper(func): # 被装饰对象 def inner(*args, **kwargs): # 被装饰对象的参数 # 调用前增加新功能 start_time = time.time() # 调用被装饰对象,并接收返回值 res = func(*args, **kwargs) # 调用后添加新功能 end_time = time.time() print(end_time - start_time) return res return inner # func函数需要执行3秒 # 无参装饰器 # 使用装饰器 @wrapper # wrapper(func) ---> func def func(): time.sleep(3) func() # # 不用装饰器 # def func2(): # time.sleep(3) # # func() 举例如下 import time def download_record(func): def inner_movie(a,c): # url = 'https://www.cnblogs.com/wangeraaa/p/10236180.html' start_time = time.time() res = func(a,c) end_time = time.time() print(f'下载时间:{end_time - start_time}') print(res) return inner_movie # download_movie = download_record(download_movie) # download_movie('avd',c = 'dfe') @download_record def download_movie(a,c): print(f'{a,c}电影开始下载......') time.sleep(2) print('电影下载完成......') return '太阳.mp4' download_movie('ss','fff') >>>>>>>>>> ('ss', 'fff')电影开始下载...... 电影下载完成...... 下载时间:2.0004498958587646 太阳.mp4