有没有可能写出这样的代码:
class Test(object):
def _decorator(self, foo):
foo()
@self._decorator
def bar(self):
pass
这个失败了:@self 中的 self 是未知的。
我还尝试过:
@Test._decorator(self)
也失败了:测试未知
我想暂时更改装饰器中的一些实例变量,然后运行装饰方法,再将它们改回来。
import functools
import datetime
class Decorator(object):
def __init__(self):
pass
def execution_time(func):
@functools.wraps(func)
def wrap(self, *args, **kwargs):
""" Wrapper Function """
start = datetime.datetime.now()
Tem = func(self, *args, **kwargs)
end = datetime.datetime.now()
print("Exection Time:{}".format(end-start))
return Tem
return wrap
class Test(Decorator):
def __init__(self):
self._MethodName = Test.funca.__name__
@Decorator.execution_time
def funca(self):
print("Running Function : {}".format(self._MethodName))
return True
if __name__ == "__main__":
obj = Test()
data = obj.funca()
print(data)
import functools
class Test:
@staticmethod
def _decorator(f):
@functools.wraps(f)
def _wrapper(self, *args, **kwargs):
# do some serious decorating (incl. calls to self!)
print(self)
return f(self, *args, **kwargs)
return _wrapper
@_decorator
def bar(self):
return 42
import decorator
class Test(object):
@decorator.decorator
def _decorator(foo, self):
foo(self)
@_decorator
def bar(self):
pass
def methoddecorator(deco: Callable[[Any, Callable], Callable]):
"""
Decorator to implement method decorators in the same class
Example of usage:
class A:
@methoddecorator
def my_methods_deco(self, method):
@wraps(method)
def wrapper(this: 'A', *args, **kwargs):
# do smth
# N.B. for instance access use this, not self!
return method(this, *args, **kwargs)
return wrapper
@my_methods_deco
def my_method(self, a, b):
...
"""
@functools.wraps(deco)
def wrapped_deco(method):
return deco(NotImplemented, method)
return wrapped_deco
@deco(param=...)
这样的装饰器参数,但是更复杂的代码可以支持。def methoddecorator(deco):
"""
Decorator to implement method decorators in the same class
Supports optionally parametrized decorators
Example of usage:
class A:
@methoddecorator
def my_methods_deco(self, _method=None, param1=None, param2=None):
@wraps(method)
def wrapper(this: 'A', *args, **kwargs):
# do smth
# deco params are also available here
return method(this, *args, **kwargs)
return wrapper
@my_methods_deco
def my_method1(self, a, b):
...
@my_methods_deco(param1=11, param2=12)
def my_method2(self, a, b):
...
"""
@wraps(deco)
def wrapped_deco(_method=None, **kwargs):
return (
deco(NotImplemented, _method)
if _method is not None
else partial(deco, NotImplemented, **kwargs)
)
return wrapped_deco