列表
为什么需要列表
前面学变量的时候,一个名字只装一个值:
a = 1
b = 2
c = 3
存一个数、一个名字,这样够用。可是如果要存全班 50 个同学的姓名呢?难道要起 50 个名字、写 50 行赋值?显然太笨了。
我们需要一种能一次装下很多值的东西,这就是列表(list)。
names = ["tom", "jerry", "spike"]
print(names)
['tom', 'jerry', 'spike']
列表用方括号 [] 表示,里面的值用逗号隔开。它像一排有编号的盒子:盒子按顺序排好,每个盒子放一个值。
列表里可以放数字、字符串,也可以混着放,甚至可以再放一个列表。
l = [1, "hello", 3.14, True]
print(l)
[1, 'hello', 3.14, True]
下标:从 0 开始
每个盒子都有编号,叫做下标。编号从 0 开始,不是从 1 开始,这是编程里常见的习惯。
第一个元素是 l[0],第二个是 l[1],第 n 个是 l[n-1]。
l1 = [1, 2, 3, 4]
print(l1[0])
print(l1[1])
print(l1[3])
1
2
4
l1[3] 取出的是第 4 个元素。数下标时要记住「从 0 数」。
用 -1 取最后一个
如果列表很长,我们往往不知道最后一个的下标是多少。用负数下标可以从末尾往回数:-1 是最后一个,-2 是倒数第二个。
l = ["a", "b", "c"]
print(l[-1])
print(l[-2])
c
b
这样不管列表多长,l[-1] 总是最后一个。
修改元素
列表和字符串有一个重要区别:字符串里的字符改不了,列表可以按下标直接改。
l = [1, 2, 3]
print(l)
l[0] = 100
print(l)
[1, 2, 3]
[100, 2, 3]
这一句 l[0] = 100 把第一个盒子里的值换成了 100。列表因此也叫「可变」的。
切片:取一段
要一次取出连续的几个元素,用切片:l[起点:终点]。规则是包含起点,不包含终点。
l = [1, 2, 3, 4, 5]
print(l[1:3])
print(l[:2])
print(l[2:])
[2, 3]
[1, 2]
[3, 4, 5]
l[1:3]从下标 1 取到下标 2,不包含 3l[:2]省略起点,从最前面开始l[2:]省略终点,一直取到最后
切片得到的是新列表,改动它不会影响原来的列表。这一点后面会再提到。详见 切片。
长度和遍历
len(l) 得到列表里元素的个数。
l = ["tom", "jerry", "spike"]
print(len(l))
3
要逐个处理每个元素,用 for 遍历,不用自己管下标:
for name in l:
print(name)
tom
jerry
spike
如果同时需要下标和值,用 enumerate。它是内置函数,括号里能放哪些类型,见 for 循环。
for i, name in enumerate(l):
print(i, name)
0 tom
1 jerry
2 spike
判断元素是否存在
用 in 判断某个值在不在列表里,结果是 True 或 False。
l = ["tom", "jerry"]
print("tom" in l)
print("spike" in l)
True
False
列表可以嵌套
列表里还能放列表,像表格一样按行、列两层下标访问。
grid = [[1, 2], [3, 4]]
print(grid[0])
print(grid[1][0])
[1, 2]
3
grid[1][0] 先取第 2 行,再取这一行的第 1 个元素。
排序
sort 直接改原列表,sorted 返回一个新列表、原列表不动。加 reverse=True 可以从大到小。
nums = [3, 1, 2]
print(sorted(nums))
print(nums)
nums.sort()
print(nums)
print(sorted(nums, reverse=True))
[1, 2, 3]
[3, 1, 2]
[1, 2, 3]
[3, 2, 1]
注意第 4 行打印 nums 还是 [3, 1, 2],说明 sorted 没有动原列表。
列表推导式
如果要把一个列表里的每个元素都算一遍,得到一个新列表,可以用列表推导式,写起来更短。
nums = [0, 1, 2, 3, 4]
squares = [n * n for n in nums]
print(squares)
odds = [n for n in nums if n % 2 == 1]
print(odds)
[0, 1, 4, 9, 16]
[1, 3]
[n * n for n in nums]把每个元素平方[n for n in nums if n % 2 == 1]只留下奇数
一开始看不懂不要紧,先用 for 循环写,等熟悉了再用这种写法。
合并和重复
两个列表可以用 + 拼起来,用 * 重复若干次。
a = [1, 2]
b = [3, 4]
print(a + b)
print(a * 2)
print([0] * 3)
[1, 2, 3, 4]
[1, 2, 1, 2]
[0, 0, 0]
[0] * 3 常用来一次造出一个全是 0 的列表。
常见坑
切片是新列表,改它不影响原列表。
l = [1, 2, 3]
part = l[:2]
part[0] = 100
print(part)
print(l)
[100, 2]
[1, 2, 3]
但 b = a 不复制,只是又起了个名字。
a = [1, 2, 3]
b = a
b.append(4)
print(a)
[1, 2, 3, 4]
两个名字指向同一个列表,改一个另一个也跟着变。真要独立一份,用 b = a[:] 或 b = list(a)。
下标越界会报 IndexError。
l = [1, 2, 3]
print(l[3])
IndexError: list index out of range
列表只有下标 0、1、2,没有 3,所以报错。
小结
- 列表用来存一组有顺序的值,用
[]表示 - 下标从 0 开始,负数从末尾数
- 列表可修改,字符串不可修改
l[起点:终点]做切片,切片是新列表len看长度,for遍历,in判断存在sort改原列表,sorted返回新列表b = a不复制,b = a[:]才复制- 常用的追加、删除、插入见 列表函数
用 python examples/list.py 运行本节的例子。