day12 十二、开放封闭、装饰器
一、nonlocal关键词
1、作用:将local和enclosing(e中的名字需要提前定义)中的名字统一
2、应用场景:如果想在被嵌套的函数中修改外部函数变量(名字)的值
3、案例
- def outer():
- num = 0
- print(num) # 结果为 0
- def inner(): # 如果想在被嵌套的函数中修改外部函数变量(名字)的值
- nonlocal num # 将L与E(E中的名字需要提前定义)的名字统一
- num = 100
- print(num) # 结果为 100
- inner()
- print(num) # 结果为 100
- outer()
- num =100
- def fn():
- global num
- num = 10
- def fn2():
- global num
- num = 20
- fn2()
- fn()
- print(num)
二、开放封闭原则
1、定义:不能修改源代码,不能更改调用方式,但可以对外提供增加新功能的特性
2、开放:修改了源代码,没有更改调用方式,对外调用方式还是原来的,但功能有所增加,不能更改被装饰对象(函数)的调用方式,且达到了增加功能的效果
- def fn():
- print('fn run1')
- print('fn run')
- print('fn run3')
- fn()
3、封闭:没有修改源代码,但更改了调用方式 。
不能修改被被装饰对象(函数)的源代码
- def fn():
- print('fn run')
- fn()
- def wrap(fn):
- print('fn run1')
- fn()
- print('fn run3')
- fn()
- wrap(fn)
三、装饰器
1、装饰器:闭包的一个应用场景。为一个函数添加新功能的工具
- def vase():
- print('插花')
- vase() # 结果为 插花
- # 增加一个绘画观赏功能:不满足封闭开放原则,修改了源代码
- def vase():
- print('插花')
- print('绘画观赏')
- vase()
- # 结果为
- # 插花
- # 绘画观赏
- # 增加一个绘画观赏功能,不满足开放封闭原则,更改了调用方式
- def vase():
- print('插花')
- vase()
- def wrap(vase):
- vase()
- print('绘画观赏')
- wrap(vase)
- def vase():
- print('插花')
- def wrap(vase):
- def fn():
- print('绘画观赏')
- return fn
- vase = wrap(vase)
- vase()
- def vase():
- print('插花')
- # 下方的函数嵌套结构就是装饰器*****
- def wrap(x): #x=vase
- def fn():
- x() # 原有的vase
- print('绘画:进行观赏')
- return fn # 拓展功能后的vase
- vase = wrap(vase) # 将拓展功能后的功能函数重新赋值给vase
- vase() # 功能拓展了,且调用方式不变
2、装饰器简化语法
- def outer(fn):
- def inner():
- fn()
- print('绘画观赏')
- return inner
- def wrap(fn):
- def inner():
- fn()
- print('摆放功能')
- return inner
- # 语法糖|笑笑语法
- @wrap # 总结:一个函数可以被任意一个装饰器装饰,也可以被任意几个装饰器装饰
- @outer # 装饰的顺序会影响新增功能的执行顺序
- def vase():
- print('插花')
- vase()
- # 结果为
- # 插花
- # 绘画观赏
- # 摆放功能
四、有参有反的函数被装饰
- 案例
- # 增加一个账号处理功能:3位及以上英文字符或汉字
- def check_usr(fn):
- def inner(usr, pwd):
- if not (len(usr) >= 3 and usr.isalpha()):
- print('账号验证失败')
- return False
- result = fn(usr, pwd) # login
- return result
- return inner
- # 增加一个密码处理功能:6位及以上英文和数字
- def check_pwd(fn):
- def inner(usr, pwd):
- if not (len(pwd) >= 6 and pwd.isalnum()):
- print('密码验证失败')
- return False
- return fn(usr, pwd)
- return inner
- # 登录功能
- @check_usr # login = check_usr(login) = inner
- @check_pwd
- def login(usr, pwd):
- if usr == 'abc' and pwd =='123qwe':
- print('登录成功')
- return True
- print('登录失败')
- return False
- res = login('abc', '123qwe') # inner
- print(res)
五、登录认证案例
- is_login = False # 登录状态
- def login():
- usr = input('usr: ')
- if not (len(usr) >= 3 and usr.isalpha()):
- print('账号验证失败')
- return False
- pwd = input('pwd: ')
- if usr == 'abc' and pwd =='123qwe':
- print('登录成功')
- is_login = True
- else:
- print('登录失败')
- is_login = False
- # 完成一个登录状态校验的装饰器
- def check_login(fn):
- def inner(*args, **kwargs):
- # 查看个人主页或销售功能前:如果没有登录先登录,反之可以进入其功能
- if is_login != True:
- print('你未登录')
- login()
- # 查看个人主页或销售
- result = fn(*args, **kwargs)
- return result
- return inner
- # 查看个人主页功能
- @check_login
- def home():
- print('个人主页')
- # 销售功能
- @check_login
- def sell():
- print('可以销售')
- home()
五、案例
1、写出完整的装饰器(不用考虑带参装饰器,就是普通装饰器)语法
- def wrapper(func):
- def inner(*args, **kwargs):
- pass
- result = func(*args, **kwargs)
- pass
- return result
- return inner
2、有一个计算两个数和的方法,为其添加一个确保两个参数都是int或float类型的装饰器,保证运算不会抛异常
- def check_num(func):
- def inner(n1, n2):
- b1 = isinstance(n1, int) or isinstance(n1, float)
- b2 = isinstance(n2, int) or isinstance(n2, float)
- if not (b1 and b2):
- print('不能求和')
- return # 结束掉,不让其进入计算功能
- return func(n1, n2)
- return inner
- @check_num
- def add(n1, n2):
- return n1 + n2
- print(add(1, ''))
3、有一个一次性录入人名并返回人名的方法(人名只考虑存英文),为其添加一个装饰器,使得处理后人名首字母一定大写
- def upper_name(func):
- def inner():
- result = func()
- return result.title() # Owen
- return inner
- @upper_name
- def get_name():
- name = input('name: ') # owen
- return name
- print(get_name())
day12 十二、开放封闭、装饰器的更多相关文章
- 十二、Decorator 装饰器模式
设计: 代码清单: Display public abstract class Display { public abstract int getColumns(); public abstract ...
- 十. Python基础(10)--装饰器
十. Python基础(10)--装饰器 1 ● 装饰器 A decorator is a function that take a function as an argument and retur ...
- Python小白学习之路(二十四)—【装饰器】
装饰器 一.装饰器的本质 装饰器的本质就是函数,功能就是为其他函数添加附加功能. 利用装饰器给其他函数添加附加功能时的原则: 1.不能修改被修饰函数的源代码 2.不能修改被修饰函数的调用 ...
- Python小白学习之路(二十五)—【装饰器的应用】
通过一个任务来加深对装饰器的理解和应用 回顾:装饰器的框架 def timmer(func): def wrapper(): func() return wrapper 任务:给以下正在运行的程序加一 ...
- python学习 day12 (3月18日)----(装饰器内置函数)
读时间函数: # import time # def func(): # start_time = time.time() # 代码运行之前的时间 # print('这是一个func函数') # ti ...
- python 二——函数、装饰器、生成器、面向对象编程(初级)
本节内容 1.函数 2.装饰器 3.生成器 4.类 一.函数 函数式:将某功能代码封装到函数中,日后便无需重复编写,仅调用函数即可 面向对象:对函数进行分类和封装,让开发“更快更好更强...” 函数式 ...
- python入门(十五):装饰器
1.装饰器(decorator):设计模式 作用:给不同的函数和方法,增加不同的公用的功能. @classmethod,@staticmethod等均是装饰器 定义一个装饰函数,函数必须返回一个闭包函 ...
- python二 总结--函数-- 装饰器
装饰器是什么? 有什么用? 为什么要用? 真的有用吗? 1.装饰器: 装饰器: 定义:本质是函数,(装饰其他函数)就是为其他函数添加附加功能. 原则:1.不能修改被装饰的函数的源代码 ...
- (二)Python 装饰器
1. 函数 在 Python 中,使用关键字 def 和一个函数名以及一个可选的参数列表来定义函数.函数使用 return 关键字来返回值.定义和使用一个最简单的函数例子: >>> ...
随机推荐
- Javascript 函数声明、函数表达式与匿名函数自执行表达式
函数表达式(Function Expression)注:将函数定义为表达式语句(通常是变量赋值)的一部分 //func() 错误 var func = function () { } //func() ...
- 开发app前需要提前准备的资料
需要准备的资料整理如下: 1 域名未注册,建议在 阿里云注册:https://www.aliyun.com/,2 服务器https://ecs-buy.aliyun.com/配置:计费方式:包年包月地 ...
- django项目settings.py的基础配置
一个新的django项目初始需要配置settings.py文件: 1. 项目路径配置 新建一个apps文件夹,把所有的项目都放在apps文件夹下,比如apps下有一个message项目,如果不进行此项 ...
- C# Task中的Func, Action, Async与Await的使用
在说Asnc和Await之前,先说明一下Func和Action委托, Task任务的基础的用法 1. Func Func是一种委托,这是在3.5里面新增的,2.0里面我们使用委托是用Delegate, ...
- linux服务查看
(1)#service servicename status比如查看防火墙:#service iptables status (2)#chkconfig --list |grep 服务名 比如查看te ...
- 解决SVN 每次操作都需要重输入用户名密码问题
把目录C:\Users\当前账号\AppData\Roaming\Subversion\auth下的文件删除,然后重启hbuilder或eclipse工具,重新输入账号密码之后,保存即可解决该问题.
- SAP 生产订单变更管理 OCM Order Changement Management
SAP OCM Order Changement Management 一.目的 订单变更管理系统是当我们的订单(生产订单.计划订单.采购订单)已经存在的时候,其物料主数据或销售数据有变更时,我们可 ...
- (原)关于udp的socket发送数据耗时的问题探讨
转载请注明出处:http://www.cnblogs.com/lihaiping/p/6811791.html 本学习笔记,仅用于问题探讨,如有不同,可以讨论. 最近在看流媒体分发服务器的相关代码,其 ...
- ubuntu更改镜像源
参考 https://blog.csdn.net/weixin_41762173/article/details/79480832 建议使用ustc.edu的源,其他例如清华的,阿里的连sublime ...
- Git命令行大全
git branch 查看本地所有分支 git status 查看当前状态 git commit 提交 git branch -a 查看所有的分支 git branch -r 查看远程所有分支 git ...