def deco(*args):
def _deco(func):
def __deco():
print("before %s called [%s]." % (func.__name__, args))
func()
print(" after %s called [%s]." % (func.__name__, args))
return __deco
return _deco
@deco("mymodule") # 可用
def myfunc():
print(" myfunc() called.")
@deco() # 也可用
def myfunc2():
print(" myfunc2() called.")
@deco # 报错 TypeError: _deco() takes exactly 1 argument
def myfunc3():
print(" myfunc2() called.")
myfunc()
myfunc2()
myfunc3()
没有参数的 @deco
其实就是 deco(myfunc3)
,所以需要对参数做个判断就行。
import types
def deco(*args):
def _deco(func):
def __deco():
print("before %s called [%s]." % (func.__name__, args))
func()
print(" after %s called [%s]." % (func.__name__, args))
return __deco
# 当直接使用 @deco 定义的时候第一个参数为函数
if len(args) == 1 and type(args[0]) is types.FunctionType:
return _deco(args[0])
return _deco
def decorator(func_text):
def decorator1(func):
def wapper(*args, **kw):
print 'before func...%s' % func_text
func(*args, **kw)
print 'after func...%s' % func_text
return wapper
def decorator2(*args, **kw):
print "before...%s" % func_text.__name__
func_text(*args, **kw)
print "after...%s" % func_text.__name__
if hasattr(func_text, '__call__'):
return decorator2
else:
return decorator
@decorator
def foo2(a,b):
print a
print b
print "foo2"
@decorator('decorator')
def foo3(a,b):
print a
print b
print "foo3"
foo2('a', 'b')
foo3('a', 'b')
@deco 和 @deco()是不一样的