如何更改基类
我有一个类,它是从一个基础类派生出来的,代码行数非常多。
比如:
class AutoComplete(TextCtrl):
.....
我想做的是修改这个基础类,让它像这样工作:
class AutoComplete(PriceCtrl):
.....
我需要这两种自动补全的功能,可能还想添加更多的基础类,那么我该如何动态地实现呢?
组合模式本来是个解决办法,但我不想大幅度修改代码。
有没有简单的解决方案呢?
3 个回答
1
你可以修改 __bases__
这个元组。比如说,你可以添加一个新的基类:
AutoComplete.__bases__ += (PriceCtrl,)
不过一般来说,我建议尽量避免这种小把戏,因为这样很快就会搞得一团糟。
2
你可以使用多重继承来实现这个:
class AutoCompleteBase(object):
# code for your class
# remember to call base implementation with super:
# super(AutoCompleteBase, self).some_method()
class TextAutoComplete(AutoCompleteBase, TextCtrl):
pass
class PriceAutoComplete(AutoCompleteBase, PriceCtrl):
pass
另外,还有一个选择是使用元类:
class BasesToSeparateClassesMeta(type):
"""Metaclass to create a separate childclass for each base.
NB: doesn't create a class but a list of classes."""
def __new__(self, name, bases, dct):
classes = []
for base in bases:
cls = type.__new__(self, name, (base,), dct)
# Need to init explicitly because not returning a class
type.__init__(cls, name, (base,), dct)
classes.append(cls)
return classes
class autocompletes(TextCtrl, PriceCtrl):
__metaclass__ = BasesToSeparateClassesMeta
# Rest of the code
TextAutoComplete, PriceAutoComplete = autocompletes
不过我还是建议使用之前提到的类工厂方法,缩进一层其实并没有那么麻烦。
7
你可以为你的类创建一个工厂:
def completefactory(baseclass):
class AutoComplete(baseclass):
pass
return AutoComplete
然后可以这样使用:
TextAutoComplete = completefactory(TextCtrl)
PriceAutoComplete = completefactory(PriceCtrl)
另一方面,根据你想要实现的目标和你的类的结构,可能AutoComplete是一个混合类,这样你就可以用下面的方式定义 TextAutoComplete
:
class TextAutocomplete(TextCtrl, AutoComplete):
pass