如何在Python 3中实现切片?
我看了一些关于Python 3中切片(slice)的内容。然后我写了一个程序,尝试实现 __getitem__(self, slice(s))
。下面是我的代码:
class NewList:
def __init__(self, lst):
print('new list')
self._list = lst
def __getitem__(self, x):
if type(x) is slice:
return [ self._list[n] for n in range(x.start, x.stop, x.step) ] #error?
else:
return self._list[x]
...
nl1 = NewList([1,2,3,4,5])
nl1[1:3] #error occurs
然后我发现 x.step
是 None
,这导致范围(range)抛出了一个异常。那么,我应该怎么实现 __getitem__
方法呢?
4 个回答
1
如果x
是一个切片,你可以像其他条件一样进行操作:
return self._list[x]
4
如果你不知道你的对象有多长,其实有一个简单的方法可以绕过这个必须要提供的参数。比如说,一个无限序列的getitem可以这样写:
def __getitem__( self, key ) :
if isinstance( key, slice ) :
m = max(key.start, key.stop)
return [self[ii] for ii in xrange(*key.indices(m+1))]
elif isinstance( key, int ) :
#Handle int indices
这样的话,只有在你不提供开始和结束的时候才会出错,不过通过检查是否为None,这个问题也可以解决。
5
你需要使用 slice.indices
这个方法。给定你序列的长度,它会返回一个包含开始位置、结束位置和步长的元组:
>>> s = slice(2, 5, None)
>>> s.indices(10)
(2, 5, 1)
>>> [x for x in range(*s.indices(10))]
[2, 3, 4]
>>> s.indices(3)
(2, 3, 1)
>>> s.indices(0)
(0, 0, 1)