python装饰器应该算是面试常考到的用点,之前在flask的应用中也是会常常用到,抽空仔细看书查资料理解了下装饰器的概念,通过自己的理解记忆,应该对这个概念会有一个大致上具体的了解。
闭包
说起python装饰器,我们应该不得不谈谈闭包的概念。
我对闭包的理解是,当函数存在嵌套,子函数调用了父函数的变量,那么子函数体加上父函数中调用的变量,那么这时候子函数加上这个调用的变量,就形成了一个闭包。如果子函数没有调用父函数的变量,那么就不存在闭包。我们可以来看一段代码:
In [7]: def fun1():
...: a,b,c = 1,2,3
...: def fun2():
...: x = 1
...: return x+a
...: return fun2
...:
In [8]: foo = fun1()
In [9]: foo()
Out[9]: 2
在这里,fun2
和fun1
中的a
形成了一个闭包。每次调用父函数中的值的时候,就会产生一个新的闭包,如果我这里用的是b
或者c
,那么会产生不一样的闭包。
我们可以发现,在这里,我们传递的是一个整数。当我们传递的是一个函数的时候,那么就成了一个装饰器。装饰器的本质就是函数闭包,利用了函数闭包的特性
装饰器
In [3]: def decorator(func):
...: def wrapped():
...: print "{} is running".format(func.__name__)
...: return func()
...: return wrapped
...:
In [4]: def foo():
...: print "I'm the function"
...:
In [5]: wrapped_func = decorator(foo)
In [6]: wrapped_func()
foo is running
I'm the function
在这里decorator
就是装饰器,它将func
包装起来这里的代码相当繁琐,这时候我们可以用python的语法糖来进行修饰@
。代码如下
In [9]: @decorator
...: def bar():
...: print "I'm the guy"
...:
In [11]: bar()
bar is running
I'm the guy
这里只是简单的装饰器的用法,后续还会讨论分析其他的用法