def my_shiny_new_decorator(a_function_to_decorate):
# 在函数里面,装饰器在运行中定义函数: 包装.
# 这个函数将被包装在原始函数的外面,所以可以在原始函数之前和之后执行其他代码..
def the_wrapper_around_the_original_function():
# 把要在原始函数被调用前的代码放在这里
print ( "Beforethe function runs" )
#调用原始函数(用括号)
a_function_to_decorate()
#把要在原始函数调用后的代码放在这里
print ( "After the function runs" )
# 在这里"a_function_to_decorate" 函数永远不会被执行
# 在这里返回刚才包装过的函数
# 在包装函数里包含要在原始函数前后执行的代码.
return the_wrapper_around_the_original_function
假如你建了个函数,不想修改了
defa_stand_alone_function():
print("Iam a stand alone function , don't yyou dare modify me")
a_stand_alone_function()
#输出: I am a stand alone function, don't you dare modifyme
现在,你可以装饰它来增加它的功能,把它传递给装饰器,它就会返回一个被包装过的函数.
a_stand_alone_function_decorated =my_shiny_new_decorator(a_stand_alone_function)
a_stand_alone_function_decorated()
#输出s:
#Before the function runs
#I am a stand alone function, don't you dare modify me
#After the function runs
现在,你或许每次都想用a_stand_alone_function_decorated代替a_stand_alone_function,很简单,只需要用my_shiny_new_decorator返回的函数重写a_stand_alone_function:
a_stand_alone_function = my_shiny_new_decorator(a_stand_alone_function)
a_stand_alone_function()
#输出:
#Before the function runs
#I am a stand alone function, don't you dare modify me
#After the function runs
上述即为装饰器的作用!!!!
装饰器语法:
@my_shiny_new_decorator def another_stand_alone_function(): print("Leave me alone") another_stand_alone_function()
#输出: #Before the function runs #Leave me alone #After the function runs
@decorator就是下面的简写:
another_stand_alone_function =my_shiny_new_decorator(another_stand_alone_function)
装饰器就是decorator design pattern的pythonic的变种.在Python中有许多经典的设计模式来满足开发者.
看下面的例子:
def bread(func): def wrapper(): print("</''''''/>") func() print("</''''''/>") return wrapper def ingredients(func): def wrapper(): print("#tomatoes#") func() print("~salad~") return wrapper
def sandwich(food="--ham--"):
print(food)
执行
sandwich()
输出
# --ham--
执行
sandwich = bread(ingredients(sandwich))
sandwich()
输出
#</''''''\>
# #tomatoes#
# --ham--
# ~salad~
#<\______/>
用装饰器实现
@bread @ingredients def sandwich(food = "--ham--"): print("food")
执行
sandwich()
输出
#</''''''\>
# #tomatoes#
# --ham--
# ~salad~
#<\______/>
改变一下顺序:
@ingredients @bread def sandwich(food = "--ham--"): print("food")
执行
sandwich()
输出
##tomatoes#
#</''''''\>
# --ham--
#<\______/>
# ~salad~
结论:装饰器先写后调用,靠近里层的先调用,就像包装一样