在Python中将单个元素列表视为标量

时间:2018-11-13 20:07:22

标签: python list subclass

¿是否可以定义python列表的子类,以允许像使用标量一样使用单元素列表变量?

例如,我希望能够做到:

class CustomList(list):
    ...
    ...

list1 = CustomList([2])
list2 = CustomList([3])
list3 = CustomList([4,5,6])
list4 = CustomList([{'foo':'bar'}])
list1 #should return list1[0]
list4['foo'] #should return list4[0]['foo'] = 'bar'
list1 + list2 #should return list1[0] + list2[0] = 5

但可以正常使用列表:

for i in list3:
    print list[i]

2 个答案:

答案 0 :(得分:2)

是的,但是您实际上需要覆盖您希望它使用的任何方法。

当您在诸如列表之类的对象上调用某些运算符时,最终会在这些对象上调用隐藏方法。在您给出的示例wchar_t* moduleNameOnly = wcsrchr(szModName, L'\\')+1; 中,实际调用的函数是result = list1 + list2。如果需要,可以子类list1.__add__(list2)并重写这些方法。例如:

list

如果class CustomList(list): def __add__(self, value): if len(self) == 1 and len(value) == 1: return self[0] + value[0] else: return CustomList(list.__add__(self, value)) list1都为长度1,则将它们视为标量,否则将引用普通的list2功能。 This stackoverflow answer on subclassing list可能对您有帮助。


要解决您的编辑问题,一个更通用的解决方案将非常简单-代替覆盖list函数,尝试覆盖__add__(),只要您使用方括号运算符,就会调用该函数:

__getitem__()

但是,这在尝试连接数组时可能会导致问题。 class CustomList(list): def __getitem__(self, y): if len(self) == 1: return self[0][y] else: return self[y] 会导致错误,因为list3 + list1不可迭代,但是如果列表长度超过一个元素,当然您可以覆盖list1来简单地将第二个值添加为列表元素


使用上面的声明输出控制台:

__add__

答案 1 :(得分:0)

假设添加两个类意味着要连接两个列表,则可以执行以下操作(请注意__add__方法以了解加法的工作原理):

from collections import MutableSequence

class CustomList(MutableSequence):
    def __init__(self, data=[]):
        self._list = data 

    def __add__(self, newlist):
        return self._list + newlist._list

    def __len__(self):
        return len(self._list)

    def __getitem__(self, i):
        return self._list[i]

    def __delitem__(self, i):
        del self._list[i]

    def __setitem__(self, i, val):
        self._list[i] = val

    def __str__(self):
        return str(self._list)

    def insert(self, i, val):
        self._list.insert(i, val)