Python:带间隙的切片的更短语法?
问题描述
假设我想要Python列表中的第一个元素、第三个到第200个元素以及从第201个元素到最后一个元素的步长为3的元素。
一种方法是使用不同的索引和串联:
new_list = old_list[0:1] + old_list[3:201] + old_list[201::3]
有没有办法在old_list
上只有一个索引就能做到这一点?我想要如下所示的内容(我知道这在语法上不起作用,因为列表索引不能是列表,而且不幸的是Pythondoesn't have slice literals;我只是在寻找接近的内容):
new_list = old_list[[0, 3:201, 201::3]]
我可以通过切换到NumPy数组来实现部分功能,但我更感兴趣的是如何对原生Python列表执行此操作。我还可以创建a slice maker或类似的东西,可能还会给出一个等价的切片对象来表示我所需的所有切片的组成。
但我正在寻找不需要创建新类来管理切片的东西。我只想将切片语法连接起来,并将其提供给我的列表,让列表理解这意味着要分别获取切片,并在最后连接它们各自的结果。
解决方案
切片生成器对象(例如,来自其他问题的SliceMaker
或np.s_
)可以接受多个以逗号分隔的切片;它们作为slice
或其他对象的tuple
接收:
from numpy import s_
s_[0, 3:5, 6::3]
Out[1]: (0, slice(3, 5, None), slice(6, None, 3))
NumPy将其用于多维数组,但您可以将其用于切片串联:
def xslice(arr, slices):
if isinstance(slices, tuple):
return sum((arr[s] if isinstance(s, slice) else [arr[s]] for s in slices), [])
elif isinstance(slices, slice):
return arr[slices]
else:
return [arr[slices]]
xslice(list(range(10)), s_[0, 3:5, 6::3])
Out[1]: [0, 3, 4, 6, 9]
xslice(list(range(10)), s_[1])
Out[2]: [1]
xslice(list(range(10)), s_[:])
Out[3]: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
相关文章