使用 .* 自己实现这一点实际上并不太难range
。您可以对范围进行切片,它会为您完成所有复杂的算术运算:
>>> range(20)[10:]
range(10, 20)
>>> range(10, 20)[::2]
range(10, 20, 2)
>>> range(10, 20, 2)[::-3]
range(18, 8, -6)
因此,您只需要一个包含对原始序列的引用和范围的对象类。这是这样一个类的代码(我希望不要太大):
class SequenceView:
def __init__(self, sequence, range_object=None):
if range_object is None:
range_object = range(len(sequence))
self.range = range_object
self.sequence = sequence
def __getitem__(self, key):
if type(key) == slice:
return SequenceView(self.sequence, self.range[key])
else:
return self.sequence[self.range[key]]
def __setitem__(self, key, value):
self.sequence[self.range[key]] = value
def __len__(self):
return len(self.range)
def __iter__(self):
for i in self.range:
yield self.sequence[i]
def __repr__(self):
return f"SequenceView({self.sequence!r}, {self.range!r})"
def __str__(self):
if type(self.sequence) == str:
return ''.join(self)
elif type(self.sequence) in (list, tuple):
return str(type(self.sequence)(self))
else:
return repr(self)
(这在大约 5 分钟内完成,因此请确保在任何重要的地方使用它之前彻底测试它。)
用法:
>>> p = list(range(10))
>>> q = SequenceView(p)[3:6]
>>> print(q)
[3, 4, 5]
>>> q[1] = -1
>>> print(q)
[3, -1, 5]
>>> print(p)
[0, 1, 2, 3, -1, 5, 6, 7, 8, 9]
* 在 Python 3 中