# 索引和分片 ## 索引 对于一个有序序列,可以通过索引的方法来访问对应位置的值。字符串便是一个有序序列的例子,**Python**使用 `[]` 来对有序序列进行索引。 In [1]: ```py s = "hello world" s[0] ``` Out[1]: ```py 'h' ``` **Python**中索引是从 `0` 开始的,所以索引 `0` 对应与序列的第 `1` 个元素。为了得到第 `5` 个元素,需要使用索引值 `4` 。 In [2]: ```py s[4] ``` Out[2]: ```py 'o' ``` 除了正向索引,**Python**还引入了负索引值的用法,即从后向前开始计数,例如,索引 `-2` 表示倒数第 `2` 个元素: In [3]: ```py s[-2] ``` Out[3]: ```py 'l' ``` 单个索引大于等于字符串的长度时,会报错: In [4]: ```py s[11] ``` ```py --------------------------------------------------------------------------- IndexError Traceback (most recent call last) in () ----> 1 s[11] IndexError: string index out of range ``` ## 分片 分片用来从序列中提取出想要的子序列,其用法为: ```py var[lower:upper:step] ``` 其范围包括 `lower` ,但不包括 `upper` ,即 `[lower, upper)`, `step` 表示取值间隔大小,如果没有默认为`1`。 In [5]: ```py s ``` Out[5]: ```py 'hello world' ``` In [6]: ```py s[1:3] ``` Out[6]: ```py 'el' ``` 分片中包含的元素的个数为 `3-1=2` 。 也可以使用负索引来指定分片的范围: In [7]: ```py s[1:-2] ``` Out[7]: ```py 'ello wor' ``` 包括索引 `1` 但是不包括索引 `-2` 。 lower和upper可以省略,省略lower意味着从开头开始分片,省略upper意味着一直分片到结尾。 In [8]: ```py s[:3] ``` Out[8]: ```py 'hel' ``` In [9]: ```py s[-3:] ``` Out[9]: ```py 'rld' ``` In [10]: ```py s[:] ``` Out[10]: ```py 'hello world' ``` 每隔两个取一个值: In [11]: ```py s[::2] ``` Out[11]: ```py 'hlowrd' ``` 当step的值为负时,省略lower意味着从结尾开始分片,省略upper意味着一直分片到开头。 In [12]: ```py s[::-1] ``` Out[12]: ```py 'dlrow olleh' ``` 当给定的upper超出字符串的长度(注意:因为不包含upper,所以可以等于)时,Python并不会报错,不过只会计算到结尾。 In [13]: ```py s[:100] ``` Out[13]: ```py 'hello world' ``` ## 使用“0”作为索引开头的原因 ### 使用`[low, up)`形式的原因 假设需要表示字符串 `hello` 中的内部子串 `el` : | 方式 | `[low, up)` | `(low, up]` | `(lower, upper)` | `[lower, upper]` | | --- | --- | --- | --- | --- | | 表示 | `[1,3)` | `(0,2]` | `(0,3)` | `[1,2]` | | 序列长度 | `up - low` | `up - low` | `up - low - 1` | `up - low + 1` | 对长度来说,前两种方式比较好,因为不需要烦人的加一减一。 现在只考虑前两种方法,假设要表示字符串`hello`中的从头开始的子串`hel`: | 方式 | `[low, up)` | `(low, up]` | | --- | --- | --- | | 表示 | `[0,3)` | `(-1,2]` | | 序列长度 | `up - low` | `up - low` | 第二种表示方法从`-1`开始,不是很好,所以选择使用第一种`[low, up)`的形式。 ### 使用0-base的形式 > Just to beautiful to ignore. > ----Guido van Rossum 两种简单的情况: * 从头开始的n个元素; * 使用0-base:`[0, n)` * 使用1-base:`[1, n+1)` * 第`i+1`个元素到第`i+n`个元素。 * 使用0-base:`[i, n+i)` * 使用1-base:`[i+1, n+i+1)` 1-base有个`+1`部分,所以不推荐。 综合这两种原因,**Python**使用0-base的方法来进行索引。