复制位于实例中的函数
这是我想要做的一些(简化的)代码:
class a:
pass
class b:
def printSelf(self):
print self
instOfA = a()
instOfB = b()
instOfA.printSelf = instOfB.printSelf
instOfA.printSelf()
<__main__.b instance at 0x0295D238>
当我调用 instOfA.printSelf() 时,它将 self 打印为 instOfB 。
但我希望当我调用 instOfA.printSelf() 时 self 为 instOfA,当我调用 instOfB.printSelf() 时 self 为 instOfB
如果不在类 a 中手动定义 printSelf ,我该如何去做呢?
对于那些想知道为什么我想做这样的事情的人来说,这里有一个更长的例子:
#Acts as a template for aInstance. I would have several aInstances that have common rules, which are defined by an instance of the aDefinition class (though I'd have multiple rule sets too)
class aDefinitionClass:
def setInput(self, val):
self.inputStr = val
def checkInputByLength(self):
return len(self.inputStr) < 5
def checkInputByCase(self):
return self.inputStr == self.inputStr.upper()
checkInput = checkInputByLength
class aInstance(aDefinition):
inputStr = ""
def __init__(self, ruleDefinition):
self.checkInput = ruleDefinition.checkInput
aDef = aDefinitionClass()
aDef.checkInput = aDef.checkInputByCase #Changing one of the rules.
aInst = aInstance(aDef)
aInst.setInput("ABC")
aInst.checkInput()
AttributeError: aDefinitionClass instance has no attribute 'inputStr'
我意识到这有点不寻常,但我想不出其他的方法。我实际上正在尝试对实例进行子类化。如果 Python 允许的话,它会看起来像这样:
class aInstance(aDef):
inputStr = ""
Here's some (simplified) code for what I'm trying to do:
class a:
pass
class b:
def printSelf(self):
print self
instOfA = a()
instOfB = b()
instOfA.printSelf = instOfB.printSelf
instOfA.printSelf()
<__main__.b instance at 0x0295D238>
When I call instOfA.printSelf(), it prints self as being instOfB.
But I want self to be instOfA when I call instOfA.printSelf(), and instOfB when I call instOfB.printSelf()
How would I go about doing this without manually defining printSelf in class a?
To those wondering why I would even want to do something like this, here's a longer example:
#Acts as a template for aInstance. I would have several aInstances that have common rules, which are defined by an instance of the aDefinition class (though I'd have multiple rule sets too)
class aDefinitionClass:
def setInput(self, val):
self.inputStr = val
def checkInputByLength(self):
return len(self.inputStr) < 5
def checkInputByCase(self):
return self.inputStr == self.inputStr.upper()
checkInput = checkInputByLength
class aInstance(aDefinition):
inputStr = ""
def __init__(self, ruleDefinition):
self.checkInput = ruleDefinition.checkInput
aDef = aDefinitionClass()
aDef.checkInput = aDef.checkInputByCase #Changing one of the rules.
aInst = aInstance(aDef)
aInst.setInput("ABC")
aInst.checkInput()
AttributeError: aDefinitionClass instance has no attribute 'inputStr'
I realize it's a bit unusual, but I couldn't think of a different way of doing it. I'm effectively trying to subclass an instance. It'd look something like this if Python allowed it:
class aInstance(aDef):
inputStr = ""
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
你可以使用方法的描述符来获取绑定的方法:
当然,如果你不知道instOfB的类型,你可以使用
__class__
:如果
instOfA
不知道'不需要存储方法,您只需传入a
实例作为self
即可:You can use the descriptor of the method to get a bound method:
Of course, you can use
__class__
if you don't know the type of instOfB:If
instOfA
doesn't need the method stored, you can just pass in an instance ofa
asself
:问题是
instOfB.printSelf
是一个绑定方法 - 当您创建对象时,self
变量被设置为 instOfB。坦率地说,我要做的只是稍微不同地设置该函数:然后你只需做
如果你想用 instOfB 这样做:
这样有点难看,但它比 Brian 的解决方案(其中效果也很好)。
编辑:
更好的方法是使用描述符(尽管这仍然需要修改您的代码):
尽管在调用函数时您仍然必须包含对象的实例。
The issue is that
instOfB.printSelf
is a bound method - theself
variable is set to be instOfB when you create the object. What I would do, frankly, is just to set up the function slightly differently:Then you simply do
And if you want to do that with instOfB:
It's slightly uglier that way, but it's a bit cleaner and more obvious than Brian's solution (which works just fine as well).
Edit:
An even better way is to use descriptors (although this still requires modifying your code):
Though you still have to include the instance of the object when calling the function.