python装饰器执行顺序
. python 装饰器
1) 2层装饰器

def decorator(func):
# TODO
def wrapper(*args, **kwargs):
# TODO
func(*args, **kwargs)
# TODO
# TODO
return wrapper

2) 3层装饰器

def decorator3(a=0, b=0):
# TODO
def wrapper(func):
# TODO
def inner_wrapper(*args, **kwargs):
# TODO
func(*args, **kwargs)
# TODO
# TODO
return inner_wrapper
# TODO
return wrapper

此处a,b可为任意指定参数,但不可以更改。
3) 类装饰器, python中类本身是不可调用的, 需要实现__call__方法, 将类变为callable。

class decorator(object):
def __init__(self, func):
self.func = func
def __call__(self, *args, **kwargs):
# TODO
self.func(*args, **kwargs)
# TODO


class decorator2(object):
def __call__(self, func):
# TODO
def wrapper(*args, **kwargs):
# todo
func(*args, **kwargs)
# todo
# TODO
return wrapper

python装饰器使用闭包的方式提供aop的概念。不过需要注意,装饰器装饰的函数,无法通过func.__name__获得真正的函数名, 可以导入functools.wraps包装。

wraps实际上调用的update_wrapper。

2. python装饰器的执行顺序。

1 import time
2
3
4 def log(level="info"):
5 print "log"
6
7 def wrapper(f):
8 print "wrapper start"
9
10 def inner_wrapper(*args, **kwargs):
11 print "inner_wrapper start"
12 print "{0}: {1}".format(level, time.time())
13 f(*args, **kwargs)
14 print "{0}: {1}".format(level, time.time())
15 print "inner_wrapper end"
16
17 print "wrapper end"
18 return inner_wrapper
19
20 print "end"
21 return wrapper
22
23
24 def log2(f):
25 print "log2..."
26
27 def wrapper(*args, **kwargs):
28 print "log2"
29 f(*args, **kwargs)
30 print "log2"
31
32 print "log2..."
33 return wrapper
34
35
36 @log2
37 @log(level="debug")
38 def test(a, b):
39 print a, b

执行test,输出

参见:https://segmentfault.com/a/1190000007837364
多个装饰器是按从下到上的顺序执行的, 在上图的例子中,test可以简化为test=log2(log(test)), 先执行log装饰器inner_wrapper外层的,得到inner_wrapper, 此时inner_wrapper是log2, 得到log2的wrapper, 此wrapper封装的func是log的inner_wrapper, 依次顺序执行,
结果如上图所示。
python装饰器执行顺序的更多相关文章
- Python 装饰器执行顺序
Python 装饰器执行顺序 之前同事问到两个装饰器在代码中使用顺序不同会不会有什么问题,装饰器是对被装饰的函数做了一层包装,然后执行的时候执行了被包装后的函数,例如: def decorator_a ...
- Python装饰器执行顺序详解
探究多个装饰器执行顺序 装饰器是Python用于封装函数或代码的工具,网上可以搜到很多文章可以学习,我在这里要讨论的是多个装饰器执行顺序的一个迷思. 疑问 大部分涉及多个装饰器装饰的函数调用顺序时都会 ...
- Python 装饰器执行顺序迷思
Table of Contents 1. 探究多个装饰器执行顺序 1.1. 疑问 1.2. 函数和函数调用的区别 1.3. 装饰器函数在被装饰函数定义好后立即执行 1.4. 疑问的解释 2. 参考资料 ...
- Python面试题之多个装饰器执行顺序
疑问 大部分涉及多个装饰器装饰的函数调用顺序时都会说明它们是自上而下的,比如下面这个例子: def decorator_a(func): print 'Get in decorator_a' def ...
- 粗浅聊聊Python装饰器
浅析装饰器 通常情况下,给一个对象添加新功能有三种方式: 直接给对象所属的类添加方法: 使用组合:(在新类中创建原有类的对象,重复利用已有类的功能) 使用继承:(可以使用现有类的,无需重复编写原有类进 ...
- Python基础篇【第6篇】: Python装饰器
装饰器 装饰器模式(Decorator Pattern)允许向一个现有的对象添加新的功能,同时又不改变其结构.这种类型的设计模式属于结构型模式,它是作为现有的类的一个包装. 这种模式创建了一个装饰类, ...
- 理解Python装饰器
装饰器本质上是一个Python函数,它可以让其他函数在不需要做任何代码变动的前提下增加额外功能,装饰器的返回值也是一个函数对象.它经常用于有切面需求的场景,比如:插入日志.性能测试.事务处理.缓存.权 ...
- Python装饰器由浅入深
装饰器的功能在很多语言中都有,名字也不尽相同,其实它体现的是一种设计模式,强调的是开放封闭原则,更多的用于后期功能升级而不是编写新的代码.装饰器不光能装饰函数,也能装饰其他的对象,比如类,但通常,我们 ...
- python装饰器方法
前几天向几位新同事介绍项目,被问起了@login_required的实现,我说这是django框架提供的装饰器方法,验证用户是否登录,只要这样用就行了,因为自己不熟,并没有做过多解释. 今天查看dja ...
随机推荐
- odoo小数精确度
python round() 函数 Python用于四舍五入的内建函数round() ,它的定义为 意思是, 将 小数部分保留到 ndigits 指定的 小数位,也就是 精度保持到 ndigi ...
- C++11 并发指南四(<future> 详解一 std::promise 介绍)(转)
前面两讲<C++11 并发指南二(std::thread 详解)>,<C++11 并发指南三(std::mutex 详解)>分别介绍了 std::thread 和 std::m ...
- Android Studio之Activity切换动画(三)
1.上一篇文章"Android Studio之多个Activity的滑动切换(二)"中实现了多个activity之间的滑动切换,可是新切换出的activity大多是从右側进入 2. ...
- http协议的Last-Modified
$modified_time = $_SERVER['HTTP_IF_MODIFIED_SINCE']; if (strtotime($modified_time) + 3600 > time( ...
- AVL平衡树的插入例程
/* **AVL平衡树插入例程 **2014-5-30 11:44:50 */ avlTree insert(elementType X, avlTree T){ if(T == NULL){ T = ...
- C++ "#"的作用和使用方法
本系列文章由 @yhl_leo 出品,转载请注明出处. 文章链接: http://blog.csdn.net/yhl_leo/article/details/48879093 1 #和##的作用和使用 ...
- Zabbix 3.0安装
Server 1. rpm安装zabbix 3.0最新的epel源 rpm -ivh http://repo.zabbix.com/zabbix/3.0/rhel/7/x86_64/zabbix-re ...
- PHP对称加密类
<?php /** * Created by PhpStorm. * User: zongbinghuang * Date: 2017/7/31 * Time: 15:13 */ namespa ...
- Ajax技术实现页面无刷新跳转
Ajax实现无刷新显示新的页面 <!DOCTYPE html> <html> <head> <script src="/jquery/jquery- ...
- windows常用快捷键(转载)
f1 显示当前程序或者windows的帮助内容. f2 当你选中一个文件的话,这意味着“重命名” f3 当你在桌面上的时候是打开“查找:所有文件” 对话框 f10或alt 激活当前程序的菜单栏 win ...