Python:我如何从内置列表类型继承?

PJ.*_*des 16 python inheritance list new-operator

我想为内置list类型添加一些属性,所以我写了这个:

class MyList(list):
    def __new__(cls, *args, **kwargs):
        obj = super(MyList, cls).__new__(cls, *args, **kwargs)
        obj.append('FirstMen')
        return obj

    def __init__(self, *args, **kwargs):
        self.name = 'Westeros'

    def king(self):
        print 'IronThrone'

if __name__ == '__main__':
    my_list = MyList([1, 2, 3, 4])
    print my_list
Run Code Online (Sandbox Code Playgroud)

my_list只包含元素'FirstMen'.为什么我的__new__不在这里工作?我应该如何从内置类型继承list?对于不可变类型是否相同str

Sve*_*ach 24

list类型通常在其__init__()方法中对列表进行实际初始化,因为它是可变类型的约定.只需__new__()在对不可变类型进行子类型化时覆盖.虽然您可以__new__()在子类化列表时覆盖,但对于您的用例没有太大意义.覆盖更容易__init__():

class MyList(list):
    def __init__(self, *args):
        list.__init__(self, *args)
        self.append('FirstMen')
        self.name = 'Westeros'
Run Code Online (Sandbox Code Playgroud)

另请注意,我建议不要super()在这种情况下使用.你想在list.__init__()这里打电话,而不是其他任何东西.


Wee*_*ble 8

首先,你这样做是为了理解一个练习__new__吗?如果没有,几乎可以肯定有更好的方法来做你想做的事情.你能解释一下你想在这里实现的目标吗?

也就是说,这是你的例子中发生的事情:

  1. 你调用 MyList([1,2,3,4])
  2. 这首先是调用 MyList.__new__(MyList,[1,2,3,4])
  3. 您的实现调用list.__new__(MyList,[1,2,3,4]) 这将返回一个MyList没有元素的新实例.list.__new__不会填充列表.它离开了list.__init__,从未被称为.
  4. 您的__new__方法附加'FirstMen'到空MyList实例.
  5. 您的__new__方法返回实例MyList.
  6. MyList.__init__([1,2,3,4]) 被调用.
  7. 它将name属性设置为'Westeros'.
  8. 它回来了.
  9. 实例被分配my_list并打印.

请参阅此处获取解释__new__:http://docs.python.org/reference/datamodel.html#basic-customization