我有十几个(实例)方法,它们应该仅在满足条件时才进行评估,否则返回默认值,每个方法都不同:
def fun(self, *args, **kwargs):
if not self.init():
return ... # <- default value, different for each method
# method logic
return ... # some value
我设法使用装饰器完成这项工作,如下:
from functools import partial, wraps
def check_init(caller = None, *, ret = None):
if caller is None:
return partial(check_init, ret = ret)
@wraps(caller)
def _check_init(self, *args, **kwargs):
return caller(self, *args, **kwargs) if self.init() else ret
return _check_init
class Test:
num: int = 2
def init(self) -> bool:
return self.num < 5
@check_num(ret = 'Cannot show number')
def show(self) -> str:
return 'Number is %d' % self.num
x = Test()
print(x.show()) # "Number is 2"
x.num = 4
print(x.show()) # "Number is 4"
x.num = 6
print(x.show()) # "Cannot show number"
两个问题:
由于所描述的逻辑仅与
Test
实例方法相关,因此如何将整个def check_init()
块放入Test
类中?当在课堂外时,我无法用 self
或 Test
键入提示 Self
。
有没有更好(更Pythonic)的方法来实现我想要做的事情?最好使用方法装饰器..
self
。前向引用是所需类型名称的字符串,可以在定义类型本身之前使用。def check_init(caller=None, *, ret=None):
if caller is None:
return partial(check_init, ret=ret)
@wraps(caller)
def _check_init(self: "Test", *args, **kwargs):
return caller(self, *args, **kwargs) if self.init() else ret
return _check_init
class Test:
# ...
self.init()
) 接口的混合类可能是明智之举。