上调用A类的方法取决于类型参数的
class Class1(object):
...
class Class2(object):
...
class Class3(object):
...
class A(object):
def _methA(parm1, parm2)
...
def _methB(parm1, parm2)
...
def _methC(parm1, parm2)
...
def manager(parm1, method, params)
...
if parm1.__class__.__name__==Class1.__name__:
response = _methA(parm1, params)
elif parm1.__class__.__name__==Class2.__name__:
response = _methB(parm1, params)
elif io_source.__class__.__name__==Class3.__name__:
response = _methC(parm1, params)
else:
raise Exception, "Unsupported parm1"
...
我不喜欢的方式,在manager()
if/elif
块看着它重构为这样:上调用A类的方法取决于类型参数的
def manager(parm1, method, params)
...
try:
response = {
Class1.__name__: lambda parm1, parms: _methA(parm1, parms),
Class2.__name__: lambda parm1, parms: _methB(parm1, parms),
Class3.__name__: lambda parm1, parms: _methC(parm1, parms)
}[parm1.__class__.__name__](parm1, parms)
except KeyError:
raise Exception, "Unsupported parm1"
但事实证明代码仍然在看类名困扰我 - 我真的不知道如何解释为什么... 它应该打扰我吗?
有没有更好的方式来编写代码来调用A类的方法是,根据类的参数之一,触发在不同的方法的调用?
PS。对不起这个人为的例子,但发布实际的代码会让问题变得更加复杂。我想这个问题要提炼其精髓...
这是实现多态的许多错误方法之一。你不应该看类名。查看班级名称会让你感到困扰,因为这意味着你没有正确授予责任。
将每个方法移到相应的类中。
class Class1(object):
def method(self, theA, params):
theA.methA(params)
class Class2(object):
def method(self, theA, params):
theA.methB(params)
class Class3(object):
def method(self, theA, params):
theA.methC(params)
class A(object):
def methA(parm1, parm2)
...
def methB(parm1, parm2)
...
def methC(parm1, parm2)
...
def manager(parm1, method, params)
...
param1.method(self, params)
+1表达为什么我觉得在查看类名称的代码时感到不安。 :-)是的,这是我们正在讨论的事情之一 - 为什么这些方法没有封装在Class1,Class2和Class3中。在实际的代码中有它的原因(虽然它们可能不是很好的理由)。 – cethegeek 2009-12-18 15:34:39
@celopes:“他们可能不是很好的理由” - 几乎是正确的。他们不是很好的理由。他们“似乎”使“Class1”,“Class2”和“Class3”知道“A”的特征;但是这个判断是错误的。 A的“隐藏”方法真的是* A的公共接口。 – 2009-12-18 15:40:18
我宁愿
if isinstance(parm1, Class1):
_methA(parm1, params)
elif isinstance(parm1, Class2):
_methB(parm1, params)
elif isinstance(parm1, Class3):
_methC(parm1, params)
但仍闻起来有设计缺陷的。 :)
也许你的三类ClassX
倒是应该都有一个单一的方法meth(params)
,那么你的经理可能只是打电话parm1.meth(params)
。
我通常做这种处理消息的时候,所以我没有吨IFS的...但它仍然使用了类名。一个穷人的多态性
类 - 但是,正如美国洛特说,Python支持真正的多态,为什么不使用它:对
class Handler(object):
# .. stuff
def dispatch(self, msg):
handlername = "on_%s" % type(msg)
return getattr(self, handlername, 'on_missing_handler')(msg)
def on_SomeClass(self, msg):
# msg is of SomeClass here ..
def on_SomeOtherClass(self, msg):
# msg is of SomeOtherClass here ..
def on_missing_handler(self, msg):
# there is no other handler for msg
+1:这是最小的一段代码的一个很好的例子显示问题。 – 2009-12-18 15:41:09