Python笔记·第十一章—— 函数 (二) 装饰器

一 为何要用装饰器

有的时候写完一段代码,过段时间需要对它进行升级、添加一些新功能,但是如果要直接修改原来的代码会影响其他人的调用,所以就需要一个不修改源代码且不修改原函数的调用方式的东西又能为原函数增添新功能的东西,装饰器就是干这个的。

二 什么是装饰器

装饰器他人的器具,本身可以是任意可调用对象,被装饰者也可以是任意可调用对象。
强调装饰器的原则:1 不修改被装饰对象的源代码 2 不修改被装饰对象的调用方式
装饰器的目标:在遵循1和2的前提下,为被装饰对象添加上新功能
开放封闭原则:对修改封闭,对扩展开放

三 装饰器的使用

下面是为一个函数添加装饰器,添加了计算其运行时间的功能:

 1 import time
 2 def timmer(func):
 3     def wrapper(*args,**kwargs):
 4         start_time=time.time()
 5         res=func(*args,**kwargs)
 6         stop_time=time.time()
 7         print(‘run time is %s‘ %(stop_time-start_time))
 8         return res
 9     return wrapper
10
11 @timmer
12 def foo():
13     time.sleep(3)
14     print(‘from foo‘)
15 foo()

四、装饰器语法及固定格式

1 def 装饰器函数名(func):
2     def wrapper(*args,**kwargs):
3         ret = func(*args,**kwargs)
4         return ret
5     return wrapper
6
7 @装饰器函数名
8 def func():
9    pass

五、作业练习

 1 #######################################作业练习#######################################################
 2 # 作业:
 3 # 1.编写装饰器,为多个函数加上认证的功能(用户的账号密码来源于文件),要求登录成功一次,后续的函数都无需再输入用户名和密码
 4 # user_exist = [False]
 5 # def auth(func):
 6 #     def wrapper(*args,**kwargs):
 7 #         #注册功能
 8 #         with open(‘db.txt‘,‘r‘,encoding=‘utf-8‘) as f:
 9 #             user_dic = eval(f.read())
10 #             flag = False
11 #         while not user_exist[0]:
12 #             username = input(‘请输入您的用户名:‘).strip()
13 #             password = input(‘请输入您的密码:‘).strip()
14 #             if username in user_dic and password == user_dic[username]:
15 #                 print(‘恭喜您,登录成功!‘)
16 #                 user_exist[0] = True
17 #                 break
18 #             else:
19 #                 print(‘账号或密码错误,请重新输入!‘)
20 #         ret = func(*args,**kwargs)
21 #         return ret
22 #     return wrapper
23 #
24 # @auth
25 # def func1():
26 #     print(‘函数1‘)
27 # @auth
28 # def func2(x):
29 #     print(‘函数2‘,x)
30 # func1()
31 # func2(111111)
32 # 2.编写装饰器,为多个函数加上记录调用功能,要求每次调用函数都将被调用的函数名称写入文件
33 # def log(func):
34 #     def wrapper(*args,**kwargs):
35 #         with open(‘db2.txt‘,‘a‘,encoding=‘utf-8‘) as f:
36 #             f.write(‘%s函数正在被调用。\n‘%func.__name__)
37 #         ret = func(*args,**kwargs)
38 #         return ret
39 #     return wrapper
40 # @log
41 # def func1():
42 #     print(‘func1函数被调用了。。。。‘)
43 # @log
44 # def func2():
45 #     print(‘func2函数被调用了。。。。‘)
46 #
47 # func1()
48 # func2()
49 # 进阶作业(选做):
50 # 1.编写下载网页内容的函数,要求功能是:用户传入一个url,函数返回下载页面的结果
51 from urllib.request import urlopen
52
53 # def get_html(url):
54 #     print(urlopen(url).read())
55 #
56 # get_html(‘http://www.baidu.com‘)
57 # 2.为题目1编写装饰器,实现缓存网页内容的功能:
58 # 具体:实现下载的页面存放于文件中,如果文件内有值(文件大小不为0),就优先从文件中读取网页内容,否则,就去下载,然后存到文件中
59 # from urllib.request import urlopen
60 #
61 # def get_bak(func):
62 #     def wrapper(*args,**kwargs):
63 #         with open(‘html.bak‘,‘r+‘,encoding=‘utf-8‘) as f:
64 #             if not f.read():
65 #                 ret = func(*args, **kwargs)
66 #                 print(ret)
67 #                 f.write(ret.decode(‘utf-8‘))
68 #             else:
69 #                 print(‘以下内容是从缓存中获得的^^^^^‘)
70 #                 f.seek(0)
71 #                 print(f.read())
72 #         ret = func(*args, **kwargs)
73 #         return ret
74 #     return wrapper
75 #
76 # @get_bak
77 # def get_html(url):
78 #     return urlopen(url).read()
79 # get_html(‘http://www.python.org‘)

原文地址:https://www.cnblogs.com/fu-yong/p/8135683.html

时间: 2024-10-07 23:04:59

Python笔记·第十一章—— 函数 (二) 装饰器的相关文章

python day4笔记 常用内置函数与装饰器

1.常用的python函数 abs             求绝对值 all               判断迭代器中所有的数据是否为真或者可迭代数据为空,返回真,否则返回假 any             判断迭代器中的数据是否有一个为真,有返回真,可迭代数据为空或者没有真,返回假 bin             转换整数为二进制字符串 hex            转换整数为十六进制字符串 oct             转换整数为八进制字符串 bool           转换数据为布尔值

第二模块·函数编程-第1章 函数、装饰器、迭代器、内置方法

01-鸡汤之人丑就要多读书 02-三元运算 03-文件处理 04-文件处理-二进制模式 05-文件处理-智能检测编码的工具 06-文件处理-写模式操作文件 07-文件处理-追加模式操作文件 08-文件处理-混合操作文件 09-文件操作其他功能 10-文件处理-文件修改功能 11-函数-基本介绍 12-函数-默认参数 13-函数-关键参数 14-函数-非固定参数 15-函数-非固定参数2 16-函数-返回值 17-函数-局部变量 18-函数-在函数里修改全局变量 19-函数-在函数里修改列表数据

python 类中的某个函数作为装饰器

在python的类中,制作一个装饰器的函数, class A: def wrapper(func): ###装饰器 def wrapped(self,*arg,**kwargs) ... return wrapped @ wrapper ###装饰mix def mix(): ... 当调用mix的时候,self.mix() ,会将self等参数传入 wrapper 中来吗?答案为否. 当wrapper作为装饰器的并且@wrapper这种方式作为装饰的时候,wrapper就跟普通的函数一样,仅仅

Python 基础第十一天(闭包和装饰器初识)

今日内容: 函数名的应用 闭包 装饰器的初识 装饰器的传参 1.函数名的应用 函数名是函数的名字. 本质:变量,特殊的变量.是函数的内存地址 函数名() 可以执行此函数 (1)单独打印函数名,可以得到函数的内存地址: print(func1)  # <function func1 at 0x0000000000872378> (2)函数名可以赋值 例: def func2():print(666)#f = func2print(f()) (3)函数名可以作为容器类数据的元素. 例: def f

python笔记--3--函数、生成器、装饰器、函数嵌套定义、函数柯里化

函数 函数定义语法: def 函数名([参数列表]): '''注释''' 函数体 函数形参不需要声明其类型,也不需要指定函数返回值类型 即使该函数不需要接收任何参数,也必须保留一对空的圆括号 括号后面的冒号必不可少 函数体相对于def关键字必须保持一定的空格缩进 Python允许嵌套定义函数 在定义函数时,开头部分的注释并不是必需的,但是如果为函数的定义加上这段注释的话,可以为用户提供友好的提示和使用帮助. Python是一种高级动态编程语言,变量类型是随时可以改变的.Python中的函数和自定

Python开发基础-Day7-闭包函数和装饰器基础

补充:全局变量声明及局部变量引用 python引用变量的顺序: 当前作用域局部变量->外层作用域变量->当前模块中的全局变量->python内置变量 global关键字用来在函数或其他局部作用域中使用全局变量,声明后可以在其他作用于中修改和使用 x=1 #全局赋值变量 def foo(): global x #函数内部全局声明变量x x=1111111 #函数内部修改全局变量x print(x) foo() print(x) global声明的变量在任何作用域都能够修改,所以一般非必要情

python之路 内置函数,装饰器

一.内置函数 #绝对值 abs() #所有值都为真才为真 all() #只要有一个值为真就为真 any() #10进制转成二进制 bin() #10进制转成八进制 oct() #10进制转成十六进制 hex() #布尔值 bool() #字符转换成字节 bytes() #字节转换成字符 str() #对文件的操作 open() #基本流程 #打开文件 op_file=open("file name","rwb+") #操作文件 op_file.operation()

第二模块:函数编程(学位课程):(第1章)函数、装饰器、迭代器、内置方法

1.(单选题) 在函数定义时某个形参有值,我们称这个参数为(). A位置参数 B关键字参数 C形参 D默认参数 D: 如果参数有值,我们称该参数为默认参数 关键参数,关键参数是实参,传参用的 正常情况下,给函数传参数要按顺序,不想按顺序就可以用关键参数,只需指定参数名即可(指定了参数名的参数就叫关键参数), 但记住一个要求就是,关键参数必须放在位置参数(以位置顺序确定对应关系的参数)之后 2.请问python中的变量查找作用域的顺序是什么___? 答案为LEGB LEGB 代表名字查找顺序: l

python学习笔记之函数总结--高阶函数以及装饰器

python学习笔记之函数总结--高阶函数以及装饰器 Python特点: 1.不是纯函数式编程(允许变量存在): 2.支持高阶函数(可以传入函数作为变量): 3.支持闭包(可以返回函数): 4.有限度的支持匿名函数: 高阶函数: 1.变量可以指向函数: 2.函数的参数可以接收变量: 3.一个函数可以接收另一个函数作为参数: 下面我将示例一些函数的写法以及使用,并说明python中函数的特性: 1.基本的高阶函数示例: #!/usr/bin/env python def func():