我有许多类被其他类包装起来以添加新功能。在
不幸的是,包装器类没有为它们包装的类实现传递函数,因此包装器不能与原始类互换使用。在
我想动态创建包含包装器和原始类功能的类。在
我的想法是在类中创建一个mix,并使用一个工厂将其应用于现有的类,从而动态地创建一个新的两用类。这应该允许我一次性地编写mix-in,并且混合类可以通过一个对象从mix-in提供原始功能或增强功能。在
这就是我追求的东西:
class A:
def __init__(self):
self.name = 'A'
def doA(self):
print "A:", self.name
class B(A):
def __init__(self):
self.name = 'B'
def doB(self):
print "B:", self.name
class C(A):
def __init__(self):
self.name = 'C'
def doC(self):
print "C:", self.name
class D:
def doD(self):
print "D:", self.name
class BD(B,D):
pass
def MixinFactory(name, base_class, mixin):
print "Creating %s" % name
return class(base_class, mixin) # SyntaxError: invalid syntax
a, b, c, d, bd = A(), B(), C(), D(), BD()
bd2 = MixinFactory('BD2', B, D)()
cd = MixinFactory('CD', C, D)()
a.doA() # A: A
b.doA() # A: B
b.doB() # B: B
c.doA() # A: C
c.doC() # C: C
bd.doA() # A: B
bd.doB() # B: B
bd.doD() # D: B
bd2.doA() # A: B
bd2.doB() # B: B
bd2.doD() # D: B
cd.doA() # A: C
cd.doC() # C: C
cd.doD() # D: C
问题是很明显,你不能仅仅从一个函数中返回一个类。尽管忽略了语法错误,上面的代码确实显示了我要实现的目标。在
我曾尝试过type()
的三参数变量,但无法使其发挥作用,因此我不确定这是否是正确的方法。在
我假设在Python中创建这种类型的混合工厂是可能的,那么我需要了解什么才能实现它?在
正如Niklas R评论的那样,this answer对问题Python dynamic inheritance: How to choose base class upon instance creation?提供了我的查询的解决方案,但是Ben的答案提供了更好的解释。在
实际上你可以从一个函数返回一个类。您的语法错误是您使用class关键字,就好像它是一个可以调用的函数一样。在
请记住,所有的类块都是创建一个新类,然后将您选择的名称绑定到它(在当前范围内)。所以只要在函数中放入一个类块,然后返回类!在
如ejucovy所述,您还可以直接调用
^{pr2}$type
:这是因为(通常)类块实际上是这样做的;它将类块中定义的所有名称收集到字典中,然后将类的名称、基类的元组和字典传递到
type
以构造新类。在然而,},就像您不会调用{}来创建类的新实例一样。在
type
不过是默认元类。类和其他对象一样是对象,是类的实例。大多数类都是type
的实例,但是如果涉及到另一个元类,您应该调用它而不是{mixin(大概)没有定义元类,因此它应该与
type
的子类的任何元类兼容。所以您可以使用base
的任何类:然而,S.Lott的评论似乎真的是这个问题的最佳“答案”,除非你的mixin工厂正在做比创建一个新类更复杂的事情。与提出的任何动态类创建变体相比,这要清晰得多,类型更少:
你可以在任何地方有类声明,类声明可以引用变量进行子类化。至于类名,它只是class对象上的
.__name__
属性。所以:应该这么做。在
对于一行程序,三个参数
^{pr2}$type
函数也应该起作用:相关问题 更多 >
编程相关推荐