Python列表切片详解[] [:] [::]

简介

Python切片是list的一项基本的功能,类似的代码

a = list[::10]

— 《Python核心编程中文版(第二版)》

解释一下[::n]的意思

>>> s = 'abcdefgh'
>>> s[::-1] # 可以视为翻转操作
output: 'hgfedcba'
>>>  s[::2]
output: 'aceg'

序列

  • 每一个元素通过指定一个偏移量的方式得到
  • 下标偏移量是从0开始到总元素数-1结束

序列类型操作符

序列操作符

作用

seq[ind]

获取下标为ind的元素

seq[ind1:ind2]

获取下标从ind1到ind2间的元素集合

seq * expr

序列重复expr次

seq1 + seq2

连接序列seq1和seq2

obj in seq

判断obje元素是否包含在seq中

obj not in seq

判断obj元素是否不包含在seq中

切片操作符([], [:], [::]

  • 序列类型即包含一些顺序排列的对象的一个结构
  • 访问一个数据元素的语法如下
sequence[index]
  • index是想要访问的元素对应的偏移量,
  • 可以为正:
  • 可以为负:,
  • 正索引以序列的开始为起点
  • 负索引以序列的结束为终点
  • 切片:一次性得到多个元素
sequence[starting_index:ending_index]
  • 通过这种方式可以得到从起始索引到结束索引之间的一“片”元素(不包含结束索引对应的元素)
  • 具体方式
  • 整个切片:[:]
  • 部分切片:[0:3]
  • 用步长索引来进行扩展的切片操作
  • 多出来的第三个索引值被用做步长参数
  • 可以和range()中的步长参数,或者C/C++中的for语句中的步长参数类比
>>> s = 'abcdefgh'
 >>> s[::-1] # 可以视作“翻转”操作
 'hgfedcba'
 >>> s[::2] # 隔一个取一个的操作
 'aceg'

更多内容

  • 切片索引的语法要比简单的单一元素索引灵活的多
  • 开始和结束索引值可以超过字符串的长度,
  • 即起始索引可以小于0,而对于结束索引,索引值为100的元素不存在并不会报错,即用100来作为一个长度不到100的序列的结束索引不会有什么问题
>>> s = 'abcde'
 >>> i = -1
 >>> for i in range(-1, -len(s), -1)
         print(s[:i])
     abcd
     abc
     ab
     a
  • 问题是:如何在第一次迭代的时候显示整个字符串呢?是否一种方法不用在整个循环之前加入一个额外的print方法?如何定义一个索引,代表整个的序列?
  • 方案:使用另外一个小技巧:用None作为索引值,比如,在想用要给变量作为索引来从第一个到遍历最后一个元素的时候:
>>> s = 'abcde'
 >>> for i in [None] + range(-1, -len(s), -1):
         print(s[:i])
 output:
     abcde
     abcd
     abc
     ab
     a
  • 现在这个程序符合要求了。
  • 另外一种方法:先创建一个只包含None的列表,然后用extend()函数把range()的输出添加到这个列表,或者先建立range()输出组成的列表然后再把`None插入到这个列表的最前面,然后对这个列表进行遍历
  • 然而,可变对象的内建函数extend()根本就没有返回值,此方法不通
>>> for i in [None].extend(range(-1, -len(s), -1)):
         print(s[:i])
 output:
     error
 >>> for i in range(-1, -len(s), -1).extend([None]):
         print(s[:i])

 正常输出

  • 错误发生的原因在于:[None].extend(…)