Python学习之路基础篇--11-12Python基础,函数的装饰器
对于装饰器来说,就是在不改变函数的调用的情况下,对函数的前后增加了些许功能,这完全符合函数的 开放封闭 原则。装饰器的本质 其实就是一个闭包函数。
这是一个装饰器的步骤图
def wrapper(func): #
def inner(*args,**kwargs): #
ret = func(*args,**kwargs) #
return ret #
return inner # @wrapper #shopping = wrappers(shooping) # 1 --shopping = innner
def shopping(num): #
print(num) #
return 1 # print(shopping(5)) #
这样你调 shopping 时, 真实情况是你在调用 inner 函数。如果 你想打印其函数名时打印的其实是 innner 函数。
from functools import wraps
def wrapper(func): #
@wraps(func)
def inner(*args,**kwargs): #
ret = func(*args,**kwargs) #
return ret #
return inner # @wrapper #shopping = wrappers(shooping) # 1 --shopping = innner
def shopping(num): #
print(num) #
return 1 # print(shopping(5)) #
print(shopping.__name__) #以字符串的形式获取到函数名
print(shopping.__doc__) #以字符串的形式获取到函数注释
如果用内置的模块,wraps ,就可以轻松解决这个问题,使得所有的还和以前一样,其中wraps(),中要传入参数,参数应该与外层装饰器的形参一致。
对于装饰器,如果你想取消个这装饰器的功能,现在给出的方法就只能是在装饰的外面在套一个装饰器,并设置一个定位符(一个全局变量)来控制其是否执行:
control = True
def outer(flag):
def wrapper(func):
def inner(*args,**kwargs):
if flag:
print('函数执行前')
ret = func(*args,**kwargs)
print('函数执行后')
return ret
else:
ret = func(*args, **kwargs)
return inner
return wrapper @outer(control)# shoping = outer(shopping) = wapper(shoping) = inner(shopping) 只是要多一个参数进行判断
def shopping(num):
print(num)
return 1 shopping(5)
多个装饰器进行嵌套,装饰器的糖的运行是,就近原则,离函数最近的糖先运行
def wrapper1(func): #func--shopping
def inner(*args,**kwargs):
print('000函数执行前')
ret = func(*args,**kwargs)
print('000函数执行后')
return ret
return inner def wrapper2(func): #func--inner1
def inner(*args,**kwargs):
print('111函数执行前')
ret = func(*args,**kwargs) #这里的调用其实是使用 inner1() 函数
print('111函数执行后')
return ret
return inner @wrapper2
@wrapper1
def shopping(num):
print(num)
return 1 shopping(5)
'''
111函数执行前
000函数执行前
5
000函数执行后
111函数执行后
'''
来个作业
# 在12 天作业 编写装饰器,为多个函数加上认证功能(用户的账号来源于文件),
# 要求登入一次成功,后续的函数都无需再输入用户和密码
def wrapper(func):
def inner(*args, **kwargs):
with open('ver', mode='r+',encoding='utf-8')as f:
flag = f.read()
if flag:
verification = input('>>>').strip()
if verification == 'eli123':
# f.seek(0)
f.truncate(0,)
ret = func(*args, **kwargs)
return ret
else:
ret = func(*args, **kwargs)
return ret
return inner @wrapper
def buy(num):
print('买了{}个包子'.format(num))
@wrapper
def eat(num):
print('吃了{}个包子'.format(num))
with open('ver',mode='w',encoding='utf-8') as f:
f.write('aaa')
buy(3)
eat(2)
这里利用了一个文件,在进行函数前,生成内容,然后文件中有内容时,要求验证 验证码,然后删除,方便第二次的验证。
# 2.编写装饰器,为多个函数加上记录调用功能,要求每次调用函数都将被调用的函数名称写入文件
from functools import wraps
def wrapper(func):
wraps(func)
def inner(*args, **kwargs):
with open('record',mode='a',encoding='utf-8') as f:
f.write(func.__name__ + '\n')
ret = func(*args, **kwargs)
return ret
return inner @wrapper
def buy(num):
print('买了{}个包子'.format(num))
@wrapper
def eat(num):
print('吃了{}个包子'.format(num)) buy(3)
eat(2)
与第一题相比,确实比较容易一点(之后学到时间模块,可以加入时间模块的)
Python学习之路基础篇--11-12Python基础,函数的装饰器的更多相关文章
- python学习之路入门篇
本文是up学习python过程中遇到的一些问题及总结归纳,本小节是入门篇. python基本语法 循环.分支不多赘述. 模块:一个.py文件就是一个模块. 文件和异常 模式 含义解释 “r” 读模式 ...
- python学习之路 八 :面向对象编程基础
本节重点 了解面向对象.面向过程的区别 掌握什么是类,什么是对象 掌握如何定义及使用类和对象 了解类与对象间的关系 掌握类属性和实例属性 掌握绑定方法 一.编程范式 编程即写程序or写代码 ...
- Python3基础(4)匿名函数、装饰器、生成器、迭代器、内置函数、json&pickle序列化、软件目录开发规范、不同目录间模块调用
---------------个人学习笔记--------------- ----------------本文作者吴疆-------------- ------点击此处链接至博客园原文------ 1 ...
- Python 学习之路 (一):基础
数据类型和变量 整数 在Python3中,整数可以处理任意大小的整数,不分长整型和整型, 十六进制用0x开头或者H结尾表示:0x2af ,2afH 用函数 int() 来转换字符串中的数字,里面不能包 ...
- python学习之路---day25( 网络编程基础和初识socket)
基本网络知识和初识socket一:基本知识 网线:传输电信号 集线器:将所有连接到集线器的网络设备连通起来 交换机: 升级版的集线器 网卡:接受电信号 MAC地址:物理地址: 8C-88-4B-88- ...
- python -- 返回函数、匿名函数、装饰器
返回函数 高阶函数的参数可以是函数,那么其返回值也可以是函数. 闭包 对于高阶函数,内部函数可以引用外部函数的参数和局部变量.当调用外部函数返回内部函数时,相关参数和变量都保存在返回的函数(即内部函数 ...
- Python学习之路【第一篇】-Python简介和基础入门
1.Python简介 1.1 Python是什么 相信混迹IT界的很多朋友都知道,Python是近年来最火的一个热点,没有之一.从性质上来讲它和我们熟知的C.java.php等没有什么本质的区别,也是 ...
- python学习之路基础篇(第四篇)
一.课程内容回顾 1.python基础 2.基本数据类型 (str|list|dict|tuple) 3.将字符串“老男人”转换成utf-8 s = "老男人" ret = by ...
- python学习之路-day2-pyth基础2
一. 模块初识 Python的强大之处在于他有非常丰富和强大的标准库和第三方库,第三方库存放位置:site-packages sys模块简介 导入模块 import sys 3 sys模 ...
- Python学习之路-Day1-Python基础
学习python的过程: 在茫茫的编程语言中我选择了python,因为感觉python很强大,能用到很多领域.我自己也学过一些编程语言,比如:C,java,php,html,css等.但是我感觉自己都 ...
随机推荐
- Python3+Requests-HTML+Requests-File解析本地html文件
一.说明 解析html文件我喜欢用xpath不喜欢用BeautifulSoup,Requests的作者出了Requests-HTML后一般都用Requests-HTML. 但是Requests-HTM ...
- js设置radio单选框值选中
html页面: <div> <label><input type="radio" name="sex" value="m ...
- MySQL—概念,用户的创建,主键,外键,数据类型,表格创建
MySQL DBMS,MySQL的概念,数据库分类,以前MySQL的部署中的一些概念 #DBMS:数据库管理系统,用于管理数据库的大型软件.mysql就是dbms的一种 #Mysql:是用于管理文件的 ...
- flask基础---第三篇
flask中request的一些方法 首先from flask import request 1.request.path 2.request.host 3.request.host_url from ...
- layui在open弹出层回显,解决动态select数据回显问题
//监听数据表格工具条 table.on('tool(contentList)', function(obj){ //注:tool是工具条事件名,test是table原始容器的属性 l ...
- 关于WCF服务 http://XXXXXX/XXX/xxx.svc不支持内容类型 application/sop+xml;charset=utf-8 错误解决方法
有时候用IIS部署一个WCF服务时,无论是在客户端还是在服务端通过地址都能正常访问. 但是当你在客户端添加服务引用时, 怎么也添加不上, 会碰到了如下错误: 好啦. 现在说说怎么解决吧. 其实很简单. ...
- AOP面向切面编程JAVA动态代理实现用户权限管理(实现篇)
java动态代理机制的功能十分强大,使用动态代理技术能够有效的降低应用中各个对象之间的耦合紧密程度,提高开发的效率以及程序的可维护性,事实上Spring AOP就是建立在Java动态代理的基础之上.其 ...
- 关于angular实现表单的一些问题
如何用angular实现表单的一些问题?核心步骤大概如下: 创建模型类 创建控制此表单的组件. 创建具有初始表单布局的模板. 使用ngModel双向数据绑定语法把数据属性绑定到每个表单输入控件. 往每 ...
- 把玩Fedora29操作系统
reference: https://ask.csdn.net/questions/657608 1.下载Fedora服务器版操作系统 https://getfedora.org/zh_CN/se ...
- Linux集群架构(一)
第二十八课 Linux集群架构(一) 目录 一. 集群介绍 二. keepalived介绍 三. 用keepalived配置高可用集群 四. 负载均衡集群介绍 五. LVS介绍 六. LVS调度算法 ...