如何理解python的装饰器:读《简单 12 步理解 Python 装饰器》笔记

原文:简单 12 步理解 Python 装饰器

笔记:
要想理解python装饰器,需理解以下几点(本人愚笨,需时刻提醒自己):

1、面向对象!时刻牢记python是面向对象的,python中,一切都是“对象(object)”

2、理解函数的定义和调用的区别,理解“赋值不等于调用”,理解“()”是“调用操作符”,参考下面的例子。

>>> def outer():
...     def inner():
...             print("Inside inner")	# 1
...     return inner
... 
>>> foo = outer()	# 2
>>> foo
<function outer.<locals>.inner at 0x10b6076a8>
>>> foo()		# 3
Inside inner

看上面的代码:
   #1 的位置,函数outer返回函数inner。函数inner的生命周期是依赖函数outer的,每次调用outer的时候,inner被重新定义,但如果函数outer没有返回inner,则当超出函数outer的的作用域时,函数inner的生命周期将消失。
   #2 的位置,通过函数调用操作符“()”,调用outer函数,获得的是返回值inner,并赋值给变量foo,即inner函数的一个定义(说的白话文一些,就是获得了一个指向inner函数实例的指针),但此时,并未调用inner函数
   #3 的位置,通过函数调用操作符“()”,完成了对变量(对象)foo的“调用”!也就是说,完成了对函数inner的调用,inner函数开始执行,输出打印结果。

3、闭包的概念,python支持一种名为“函数闭包”的特性,意味着“在非全局作用域定义的函数,在定义时记得外层命名空间是怎样的”,还是结合上面的代码,说白了,就是函数inner记得定义它的外层函数outer的命名空间里的参数。

>>> def outer(x):
...     def inner():
...             print (x)
...     return inner
... 
>>> print1 = outer(1)
>>> print2 = outer(2)
>>> print1()
1
>>> print2()
2

4、装饰器@:装饰器其实就是“一个以函数作为参数并返回一个替换函数”的可执行函数。

5、*args和**kwargs
再次强调:
     *表示对紧随其后的迭代器的拆包;
     **表示对紧随其后的字典对象的拆包。
或者说:
     *表示从紧随其后的迭代器中取出相应的“位置参数”
     **表示所有未捕获的“关键字参数”,都将被存储在紧随其后的字典对象中。

>>> def logger(func):
...     def inner(*args, **kwargs):
...             print ("Arguments were: %s %s" % (args, kwargs))
...             return func(*args, **kwargs)
...     return inner
... 
>>> @logger
... def foo1(x, y=1):
...     return x*y
... 
>>> @logger
... def foo2():
...     return 2
... 
>>> foo1(5, 4)	# 位置实参的传递
Arguments were: (5, 4) {}
20
>>> foo1(x=5, y=4)	#关键字实参的传递
Arguments were: () {'x': 5, 'y': 4}
20
>>> foo2()
Arguments were: () {}
2
>>> 

猜你喜欢

转载自blog.csdn.net/steventian72/article/details/85846690