python 装饰器 继承_作为基类一部分的Python装饰器不能用于装饰继承类中的成员函数...

Python decorators are fun to use, but I appear to have hit a wall due to the way arguments are passed to decorators. Here I have a decorator defined as part of a base class (the decorator will access class members hence it will require the self parameter).

class SubSystem(object):

def UpdateGUI(self, fun): #function decorator

def wrapper(*args):

self.updateGUIField(*args)

return fun(*args)

return wrapper

def updateGUIField(self, name, value):

if name in self.gui:

if type(self.gui[name]) == System.Windows.Controls.CheckBox:

self.gui[name].IsChecked = value #update checkbox on ui

elif type(self.gui[name]) == System.Windows.Controls.Slider:

self.gui[name].Value = value # update slider on ui

...

I've omitted the rest of the implementation. Now this class is a base class for various SubSystems that will inherit from it - some of the inherited classes will need to use the UpdateGUI decorator.

class DO(SubSystem):

def getport(self, port):

"""Returns the value of Digital Output port "port"."""

pass

@SubSystem.UpdateGUI

def setport(self, port, value):

"""Sets the value of Digital Output port "port"."""

pass

Once again I have omitted the function implementations as they are not relevant.

In short the problem is that while I can access the decorator defined in the base class from the inherited class by specifiying it as SubSystem.UpdateGUI, I ultimately get this TypeError when trying to use it:

unbound method UpdateGUI() must be called with SubSystem instance as first argument (got function instance instead)

This is because I have no immediately identifiable way of passing the self parameter to the decorator!

Is there a way to do this? Or have I reached the limits of the current decorator implementation in Python?

解决方案

You need to make UpdateGUI a @classmethod, and make your wrapper aware of self. A working example:

class X(object):

@classmethod

def foo(cls, fun):

def wrapper(self, *args, **kwargs):

self.write(*args, **kwargs)

return fun(self, *args, **kwargs)

return wrapper

def write(self, *args, **kwargs):

print(args, kwargs)

class Y(X):

@X.foo

def bar(self, x):

print("x:", x)

Y().bar(3)

# prints:

# (3,) {}

# x: 3

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值