python-3.x - 使用 super 进行动态类继承

标签 python-3.x object inheritance superclass

我正在尝试使用 type() 动态创建一个类,并分配一个调用 super().__init__(...) 的 __init__ 构造函数;但是,当调用 super() 时,我收到以下错误:

TypeError: super(type, obj): obj must be an instance or subtype of type

这是我的代码:

class Item():    
    def __init__(self, name, description, cost, **kwargs):
        self.name           = name
        self.description    = description
        self.cost           = cost
        self.kwargs         = kwargs

class ItemBase(Item):
    def __init__(self, name, description, cost):
        super().__init__(name, description, cost)

def __constructor__(self, n, d, c):
    super().__init__(name=n, description=d, cost=c)

item = type('Item1', (ItemBase,), {'__init__':__constructor__})
item_instance = item('MyName', 'MyDescription', 'MyCost')

为什么__constructor__方法中的super()不理解对象参数;我该如何解决这个问题?

最佳答案

解决方案 1:使用 cls = type('ClassName', ...)

请注意,如果动态创建的类被继承,sadmicrowave 的解决方案会创建一个无限循环,因为 self.__class__ 将对应于子类。

另一种不存在此问题的方法是在创建类后分配__init__,例如可以通过闭包显式链接该类。示例:

# Base class
class A():
  def __init__(self):
    print('A')

# Dynamically created class
B = type('B', (A,), {})

def __init__(self):
  print('B')
  super(B, self).__init__()

B.__init__ = __init__

# Child class
class C(B):
  def __init__(self):
    print('C')
    super().__init__()


C()  # print C, B, A

解决方案 2:使用 MyClass.__name__ = 'ClassName'

动态创建类的另一种方法是在函数内定义一个类,然后重新分配 __name____qualname__ 属性:

class A:
  
  def __init__(self):
    print(A.__name__)


def make_class(name, base):

  class Child(base):
    def __init__(self):
      print(Child.__name__)
      super().__init__()

  Child.__name__ = name
  Child.__qualname__ = name
  return Child


B = make_class('B', A)


class C(B):
  
  def __init__(self):
    print(C.__name__)
    super().__init__()

C()  # Display C B A

关于python-3.x - 使用 super 进行动态类继承,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34142895/

相关文章:

python - 如何使用 BeautifulSoup 查找元素的父标签?

python - 传递带有多个参数的字符串

PHP 类实例转 JSON

Powershell 类继承行为

java - 为什么不能在通用 catch 子句中捕获自定义异常

python - TypeError : cannot unpack non-iterable numpy. float64 对象

object - 如何在没有 nms 的情况下从 Tensorflow 对象检测 ssd-mobilenet 解码 raw_outputs/box_encodings

javascript - 为什么我的 JavaScript 对象中的属性未定义?

c++ - 我想要一个派生类指针 vector 作为基类指针

python - 如何使用selenium捕获网络流量