本章的主要内容是“列表和元组”。
概念
- 数据结构:数据结构是通过某种方式组织在一起的数据元素的集合,这些数据元素可以使数字或者字符,甚至可以是其他数据结构。
- 序列:Python包含6种内建的序列,包括列表、元组、字符串、Unicode字符串、buffer对象和xrange对象。
知识点
- 在Python中,最基本的数据结构是序列。序列中第1个元素标记为0,最后一个元素标记为-1
- 列表和元组的主要区别在于,列表可以修改,元组则不能。
- 一般来说在几乎所有的情况下列表都可以替代元组,一个例外的情况是在使用元组作为字典的键时不能使用列表。
观点
- 方法是一个与某些对象有紧密联系的函数。一般来说,方法可以这样进行调用:
对象.方法(参数)
使用序列表示一个对象的信息
可以用序列表示数据库中一个人的信息——第一个元素是姓名,第2个元素是年龄。可以编写一个列表:
>>> edward = ['Edward Gumby', 42]
因为序列可以包含另一个序列,所有可以构建一个人员的列表:
>>> edward = ['Edward Gumby', 42]
>>> john = ['John Smith', 50]
>>> database = [edward, john]
>>> database
[['Edward Gumby', 42], ['John Smith', 50]]
通用序列操作
所有的序列都可进行索引、分片、加、乘以及检查某个元素是否属于序列的成员。此外,Python还有计算序列长度、找出最大元素和最小元素的内建函数。
索引
下面的例子可以使用负索引来取出元素。
输入:
>>> greeting = 'Hello'
>>> greeting[-1]
输出:
'o'
分片
可以使用分片操作来访问一定范围内的元素。分片通过冒号相隔的两个索引来实现。
分片操作对于提取序列的一部分是很有用的。第1个索引是需要提取部分的第1个元素的编号,最后的索引是分片之后剩下部分的第1个元素的编号。
输入:
>>> numbers = [1,2,3,4,5,6,7,8,9,10]
>>> numbers[3:6]
>>> numbers[0:1]
输出:
[4, 5, 6]
[1]
分片操作的实现需要提供两个索引作为边界,第1个索引的元素包含在分片内,第2个则不包含在分片内。
如果分片所得部分包括序列结尾的元素,那么只需空最后一个索引即可。这种方法同样适用于序列开始的元素。
输入:
>>> numbers = [1,2,3,4,5,6,7,8,9,10]
>>> numbers[-3:]
>>> numbers[:3]
输出:
[8, 9, 10]
[1, 2, 3]
如果需要辅助整个序列,可以把两个下标都留空
输入:
numbers[:]
输出:
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
可以使用下列的代码指定分片的步长。步长不能是0,但可以是负数,是从右向左取数据。
输入:
numbers[0:10:2]
numbers[::4]
numbers[::-2]
输出:
[1, 3, 5, 7, 9]
[1, 5, 9]
[10, 8, 6, 4, 2]
序列相加
通过使用加号可以进行序列的连续操作:
输入:
[1,2,3] + [4,5,6]
输出:
[1, 2, 3, 4, 5, 6]
只有两种相同类型的序列才能进行连接操作。
序列乘法
输入:
'python' * 5
[42] * 10
输出:
'pythonpythonpythonpythonpython'
[42, 42, 42, 42, 42, 42, 42, 42, 42, 42]
可以使用下面的代码初始化一个长度为10的列表。
输入:
sequence = [None] * 10
sequence
输出:
[None, None, None, None, None, None, None, None, None, None]
成员资格
可以使用in运算符判断成员资格。
输入:
permissions = 'rw'
'w' in permissions
users = ['mlh','foo','bar']
'mlh' in users
输出:
True
True
列表
列表有很多专用的方法。
list函数
因为字符串不能像列表一样被修改,所以有时候根据字符串创建列表会很有用。
使用下面的代码:
text_list = list('Hello')
text_list[-1] = 'a'
text = ''.join(text_list)
print(text)
得到下面的输出:
Hella
删除元素
可以使用del函数来删除一个列表中的元素。
使用下面的代码来删除一个元素:
names = ['Alice','Bob','Cecil']
del(names[2])
names
输出:
['Alice', 'Bob']
分片赋值
使用下面的代码可以进行分片赋值:
name = list('Perl')
name[1:] = list('ython')
name
输出:
['P', 'y', 't', 'h', 'o', 'n']
分片赋值语句可以在不需要替换任何原有元素的情况下插入新的元素。
使用下面的代码:
numbers = [1,5]
numbers[1:1] = [2,3,4]
numbers
输出:
[1, 2, 3, 4, 5]
也可以通过分片赋值来删除元素。
使用下面的代码:
numbers = [1, 2, 3, 4, 5]
numbers[1:4] = []
numbers
输出:
[1, 5]
append方法
append方法用于在列表末尾追加新的对象:
lst = [1,2,3]
lst.append(4)
lst
输出:
[1, 2, 3, 4]
append方法是直接修改原来的列表而不是返回一个新的列表。
count方法
count方法用于统计某个元素在列表中出现的次数:
['to','be','or','not','to','be'].count('to')
输出:
2
再来一个例子
x = [[1,2], 1, 1, [2, 1, [1, 2]]]
x.count(1)
x.count([1,2])
输出:
2
1
extend方法
extend方法可以在列表的末尾一次性追加另一个序列中的多个值。
a = [1, 2, 3]
b = [4, 5, 6]
a.extend(b)
a
输出:
[1, 2, 3, 4, 5, 6]
extend方法和连接操作的区别:extend方法修改了被扩展的序列,而连接操作则返回一个全新的列表。
index方法
index方法用于从列表中找出某个值第一个匹配项的索引位置:
knights = ['We', 'are', 'the', 'knights', 'who', 'say', 'ni']
knights.index('who')
knights.index('aaaa')
输出:
4
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: 'aaaa' is not in list
insert方法
insert方法用于将对象插入到列表中。
numbers = [1, 2, 3, 4, 5, 6, 7]
numbers.insert(3,'four')
numbers
输出:
[1, 2, 3, 'four', 4, 5, 6, 7]
同样,insert可以用分片赋值实现。
pop方法
pop方法会溢出列表中的一个元素(默认是最后一个),并且返回该元素的值。
x = [1, 2, 3]
x.pop()
x
x.pop(0)
x
输出:
3
1
[2]
remove方法
remove方法用于移除列表中某个值的第一个匹配项:
x = ['to','be','or','not','to','be']
x.remove('be')
x
x.remove('bee')
输出:
['to', 'or', 'not', 'to', 'be']
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: list.remove(x): x not in list
可以看出,只有第一次出现的值被移除了,不存在于列表中的值不会被移除。remove方法也是修改原来的列表。
reverse方法
reverse方法将列表中的元素反向存放。
x = [1, 2, 3]
x.reverse()
x
输出:
[3, 2, 1]
sort方法
sort方法用于在原位置对列表进行排序。它修改原来的列表。
x = [4, 6, 2, 1, 7, 9]
x.sort()
x
输出:
[1, 2, 4, 6, 7, 9]
使用下面的方法得到一个排好序的列表副本:
x = [4, 6, 2, 1, 7, 9]
y = x[:]
y.sort()
x
y
输出:
[4, 6, 2, 1, 7, 9]
[1, 2, 4, 6, 7, 9]
或者使用sorted函数。
x = [4, 6, 2, 1, 7, 9]
y = sorted(x)
x
y
输出:
[4, 6, 2, 1, 7, 9]
[1, 2, 4, 6, 7, 9]
如果想把一些元素按相反的顺序排列,可以先使用sort(或者sorted),然后再调用reverse方法。
元组:不可变序列
创建元组的语法如下;
>>> 1,2,3
(1, 2, 3)
>>> (1,2,3)
(1, 2, 3)
>>> ()
()
>>> 42,
(42,)
>>> 3*(40+2,)
(42, 42, 42)
逗号是很重要的,只添加圆括号也是没用的。
tuple函数
tuple函数的功能与list函数基本上是一样的:以一个序列作为参数并把它转换为元组。
>>> tuple([1, 2, 3])
(1, 2, 3)
>>> tuple('abc')
('a', 'b', 'c')
>>> tuple((1, 2, 3))
(1, 2, 3)
基本元组操作
除了创建元组和访问元组元素之外,也没有太多其他操作。
>>> x = 1, 2, 3
>>> x[1]
2
>>> x[0:2]
(1, 2)
元组的分片还是元组。
元组的意义
元组不可替代的原因有2点:
- 元组可以在映射(和集合的成员)中当做键使用——而列表则不行。
- 元组作为很多内建函数和方法的返回值存在,也就是说你必须对元组进行处理。