Python:使用用户输入作为类名的类工厂

2024-06-01 18:49:01 发布

您现在位置:Python中文网/ 问答频道 /正文

我想动态地向超类添加类属性。此外,我想创建从这个超类动态继承的类,这些子类的名称应该取决于用户的输入。在

有一个超类“Unit”,我可以在运行时向其添加属性。这已经奏效了。在

def add_attr (cls, name, value):
    setattr(cls, name, value)

class Unit(object):
    pass

class Archer(Unit):
    pass

myArcher = Archer()
add_attr(Unit, 'strength', 5)
print "Strenght ofmyarcher: " + str(myArcher.strength)
Unit.strength = 2
print "Strenght ofmyarcher: " + str(myArcher.strength)

这将产生所需的输出:
马歇尔强度:5
马歇尔强度:2

但现在我不想预先定义子类Archer,而是让用户决定如何调用这个子类。我试过这样的方法:

^{pr2}$

但运气不好。我想我真的不明白新的东西在这里有什么用。 我想要的结果是

class Soldier(Unit):
    pass

由工厂制造。如果我用参数“Knight”调用工厂,我希望创建一个类Knight,Unit的子类。在

有什么想法吗?先谢谢你!
再见
-萨诺


Tags: 用户nameadd属性valueunit动态pass
2条回答

看看^{}内建函数。在

knight_class = type('Knight', (Unit,), {})
  • 第一个参数:新类的名称
  • 第二个参数:父类的元组
  • 第三个参数:类属性字典。在

但是在您的例子中,如果子类没有实现不同的行为,那么给Unitname属性就足够了。在

要从名称创建类,请使用class语句并指定名称。注意:

def meta(name):
    class cls(Unit):
        pass

    cls.__name__ = name
    return cls

现在我想我应该解释一下自己,等等。当您使用class语句创建一个类时,它是动态完成的,这相当于调用^{}。在

例如,以下两个片段执行相同的操作:

^{pr2}$

类型的第一个参数指定给__name__的类的名称,这基本上就结束了(使用__name__本身的唯一时间可能是在默认的__repr__()实现中)。要创建一个具有动态名称的类,实际上可以像这样调用type,或者您可以稍后更改类名。class语法的存在是有原因的,尽管它很方便,而且很容易在以后添加和更改内容。例如,如果您想添加方法,则

class X(object):
    def foo(self): print "foo"

def foo(self): print "foo"
X = type("X", (object,), {'foo':foo})

等等。所以我建议使用class语句,如果你从一开始就知道你可以这么做,你很可能会这么做。处理type等等是一个烂摊子。在

(顺便说一下,您不应该用手调用type.__new__(),而应该只调用type()

相关问题 更多 >