我有一个自定义类,它本质上是一个列表,但负索引是有效索引,而不是引用列表后面的元素。
from collections.abc import Sequence
class MultiFloorPlan(Sequence):
def __init__(self):
super().__init__()
self._floors = []
self._subfloors = []
def __eq__(self, other):
if not isinstance(other, MultiFloorPlan):
return NotImplemented
return self._subfloors == other._subfloors and self._floors == other._floors
def _reindex(self, floor):
if floor >= 0:
return self._floors, floor
return self._subfloors, -floor - 1
def __len__(self):
return len(self._subfloors) + len(self._floors)
def __getitem__(self, floor):
floor_list, floor = self._reindex(floor)
return floor_list[floor]
def __delitem__(self, floor):
floor_list, floor = self._reindex(floor)
del floor_list[floor]
def __iter__(self):
for plan in self._subfloors:
yield plan
for plan in self._floors:
yield plan
def __reversed__(self):
for plan in reversed(self._floors):
yield plan
for plan in reversed(self._subfloors):
yield plan
def __contains__(self, value):
return value in self._subfloors or value in self._floors
def append(self, subfloor=False):
if subfloor:
return self._subfloors.append(None) # For this example we append a dummy None
return self._floors.append(None) # value instead of an actual Plan instance
是否可以让内置的
enumerate
返回下限索引,而不是转换为非负整数的值?示例:
mfp = MultiFloorPlan()
for _ in range(5):
mfp.append(subfloor=False)
mfp.append(subfloor=True)
for floor, _ in enumerate(mfp):
print(floor)
# This prints 0 1 2 3 4 5 6 7 8 9, but I'd like it to print -5 -4 -3 -2 -1 0 1 2 3 4
enumerate
有第二个参数。这是您想要开始的数字。如果您知道列表中的最低索引,您可以执行类似的操作。
for floor, _ in enumerate(mfp, -5):
print(floor)
enumerate
内置函数可在任意迭代器上运行,因此它不能以针对您的类的特殊方式运行。然而,聪明的 enumerate
的 user可以产生你想要的结果,他们只需要通过传入适当的起始索引来正确设置它。您可以使用以下方法在类中提供该设置:
def enumerate(self):
return enumerate(self, -len(self._subfloors))