列表
在前面我在写 for-in 循环的时候,曾经说到过列表,但是没有细说,只是提了一句,而在前面,我就曾说过,在 for-in 循环后面只可能跟上一个容器,而列表,就是一个有序且可变的容器。
创建一个列表
list1 = []
# 利用直接赋值一个空列表来给列表初始化从而达创建列表的效果
list2 = list()
# 使用 list() 方法直接创建列表,这里 () 里面的参量存在时可以把里面的变量强制转换成
# 列表格式(list)的容器型变量
列表的性质
- 可变性:列表是一个可变的容器,它里面的数据可以增加、删除或者修改。
- 有序性:列表中的每个元素都有自己的下标,我们可以通过取下标的方式,直接拿到列表里元素。
- 宽松性:列表可以存放任意类型的元素,对其内部元素不做类型要求。
- 列表的最显著特征就是它的外部是一个 [] ,里面的元素使用 , 进行隔开。
- 列表的数据类型是 list 。(这里要注意,由于list在Python中属于关键字,所以建议不要把列表命名为 list ,容易爆 PEP:8 错误)
列表的下标及切片
下标
列表的下标就是其 [] 内的数字,用来表示列表内元素的位置关系。
列表内的元素下标从 0 开始到 len(列表) - 1 结束,这里需要记住列表等容器大部分的下标都是从0开始的,这点可能与其它语言不同。
下标可为正可为负,正数时,下标是从右边(从0开始递增1)开始计算,例如 list1[5] ,就是从右边开始第六位元素;负数时,下标从左边(从-1开始递减1)开始计算,例如 list[-5] ,就是从左边开始第5位元素。
这里需要注意:正数下标和负数转换的时候,并不是直接转换,而是要注意,正负的开始元素不一样,正时 0 开始,负时 -1 开始。
切片
"""
切片语法:
容器[start:stop:step]
start:开始参数,默认0,可以省略不写;stop:结束参数(必须赋值的一个参数);
step:为步长,决定下一个数字获取谁,默认为1,可以省略不写;
切片也是一个左闭右开区间,下一个被获取元素的下标=当前被获取元素的下标+step
"""
切片的用法大致相当于 range() 方法,这里不细说,给出例子,看一下就可以。
games = ['lol', '王者荣耀', 'PUBG', 'CF', 'DNF', 'QQ飞车']
print(games[1:5])
print(games[1:6], games[1:])
print(games[0:3], games[:3])
print(games[::2])
print(games[::-1], games[-1::-1])
print(games[::-2])
print(games[1:-2])
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2DYwgw4D-1678387432083)(C:\Users\Administrator\AppData\Roaming\Typora\typora-user-images\image-20230301140022050.png)]
列表格式类方法
列表的拼接和重复
-
拼接
列表的拼接就是列表的直接相加,对于列表来说,列表的直接相加可以使得新列表长度为老列表之和,元素种类也是老列表之和,由于列表中的元素可以重复,所以也使得相加后,可能会出现重复元素,对于列表的去重操作我们后面再说,现在只提供列表的拼接方法以及思路。
list1 = ['王者荣耀'] list2 = ['和平精英'] list3 = list1 + list2 # 这里的list3即为实现了列表拼接后的结果,list3 为 ['王者荣耀','和平精英']
-
重复
我们对列表直接做乘法可以实现列表的重复,即为对于列表的元素的重复。
list4 = [1,2,3,4] list5 = list4 * 2 # 此时,list5就为 [1,2,3,4,1,2,3,4] ,即只是简单的对于元素重复而已。
列表元素的增删改
增加
-
append() 方法
这个方法的括号中添加想要加入列表的元素,使用后,该元素将被添加到列表的最后一位,不可以选择位置。
list1 = [] list1.append(1) # list1现在的值就是[1]
需要注意,这个方法一次只可以添加一个元素,但对于这个元素的类型没有要求,也就是说,即使这个元素是容器型数据,也可以正常融入,只是无法将这个容器型元素的内部元素拿出来,只能做到,“放进去是什么值它就是什么值,不会有变化”。
-
insert() 方法
这个方法是和上面 append() 方法的区别就是可以选择插入元素的位置,insert() 方法有两个参数,第一个是要插入的下标,第二个就是插入的元素。
list2 = [] list2.insert(0,'怪物猎人') # 这样我们就实现了将 '怪物猎人' 插入到列表的第一个位置。
修改
修改即为将列表中需要修改值的元素的下标取出,例如我们想修改列表 list3 的第一个元素,我们就需要直接拿出第一个元素,直接修改它的值就可以了。
list3[0]='怪物猎人崛起'
# 如此就实现了修改第一个元素
删除
- del:根据下标删除元素
del games[-1]
print(games)
- remove():删除指定元素
games.remove('王者荣耀')
print(games)
- pop:根据下标删除元素,使用pop删除的元素还能被找回。
content = games.pop(0)
print(content, games)
- clear():直接清空列表
list3 = ['阿甘正传', '海王', '阿凡达', '霸王别姬', '憨豆特工', '红海行动']
list3.clear()
print(list3)
上面这几种删除元素或者列表的方法都是建立在直接修改 games 这个列表自身的基础上的。
PS:这里需要注意,pop() 方法是将元素放入电脑的回收站,我们可以进行找回操作,但是del.、remove、clear这几种方法都是直接将元素直接删除,无法再次找回。
列表的一些基础方法以及逻辑
-
index() 方法
这个方法可以对 index 的括号里的值在列表里进行检索,返回第一个和括号里值相同的元素的下标。用法如下:
list1 = [1,2,3,4,5,6] result = list1.index(1) print(result) # 这里的返回值就是0,是1在列表中的下标也就是1。
还有一种 index 使用方式,就是在括号里面第一个元素为查找对象,第二个对象为开始查找的下标,例如我们要查找 2 要从第二个元素查起,那么我们就要写成 result = list1.index(2,1)。这里需要注意,如果我们查找的元素并不在列表中,那么会发生报错,具体报错为如下情况:
list1.index(100) # 100 is not in list
-
sort() 方法
这个方法是用来对于列表进行排序,默认对列表进行升序(由小到大)。
括号中有参数 reserve 这个参数为布尔值,管控对于列表进行排序的类型,默认为 False ,为升序,True 时为降序,即从大到小排列。
list1 = [1, 2, 3, 4, 5, 6, 7, 5] list1.sort(reverse=True) print(list1)
-
sorted 函数
虽然 sorted 与列表的 sort() 在外表上很相像,但实际上,二者是存在一定差距的。
前者有返回值,返回值即为排好序的列表本身,但是并不会对列表本身造成影响,但是后者并不会返回值,并且是在列表本身造成改变,如果重新输出列表即可看到列表与原来不同,已经改变了。
print(sorted(list2, reverse=True), list2)
-
reverse() 方法
该方法与 sort() 一样,也是默认对于列表进行倒序排列,括号里写 True 或者 False 对于列表排序方式进行选择。
list4 = [1, 2, 3, 4, 5] list4.reverse() print(list4)
-
expend() 方法
这个方法被利用在对于容器内元素进行添加,旨在将括号内的容器中的全部容器加到列表里,而不需要对于列表内的每个元素拿出来之后再次进行添加,减少代码冗余,更加便捷。
list5 = [list4] list5.extend(list4) list5.extend(range(0, 9, 2)) print(list5)
需要注意的是,这个方法是对于容器类元素进行提取,也就是说,括号里的元素应当是一个容器,在处理多元素添加到列表时,这个方法会很好用,比用循环遍历拿出元素带入更快,代码冗余度更低。
PS:下面的几种方法偏数学类,在对于列表求和,求大小的方面很多都有奇效,需要细看。
-
count() 方法
对于列表中某个元素的数量进行计算,并返回这个数量值。
list1 = [ 1 , 2 , 3 , 4 , 5] print(list1.count(2))
-
sum() 方法
这个方法是对于列表进行求和,这个方法对于列表内元素要求必须是数字类型,如果是其他类型的数据,则会进行报错。
list6 = [ 1 , 2 , 3 , 4 , 5 ] print(sum(list6))
PS:这里需要注意括号里不一定是一个完整的列表,如果是列表的切片,只要切片不报错,那么就是可以正常输出值的。
-
max()、min()方法
这两个方法本质比较简单,只是对于括号内的元素求出最大值和最小值。和上一个 sum () 方法一样,同样需要注意括号里的可以是一个列表的切片,而并非只能是一个完整的列表。
print(max(list6), min(list6))
列表的大小比较
列表的大小比较主要为以下四点:
- 比较列表中元素大小的时候,比较的是列表中元素的大小,而元素的大小又取决于各类不同类型数据元素的性质,比如 int 元素就是直接比较值的大小就可以,而字符串元素则是比较元素每一位上元素的 ascii码 的大小,码较大者为大,所以还是要根据不同的元素类型来分别比较。
- 需要注意列表中参与比较的元素是一一对应的,也就是说 a 列表中的第一个元素只可以和 b 列表中的第一个元素相比较,不能和第三第四或者其他元素相比较。
- 如果两个列表的所有元素都完全一致,也没有多或者少某几个元素,那么我们就可以认为这两个列表完全相同。
- 所有比较列表的操作必须建立在两个比较的元素为同一种数据类型,如果不一样,就会发生报错现象。
列表的去重操作
先给一个例题以便后面去重:
# 例如:names = ['张三', '李四', '大黄', '张三','张三', '李四', '大黄', '张三''张三', '李四']
# -> names = ['张三', '李四', '大黄']
这里提供两种思路:
-
间接去重
names = ['张三', '李四', '大黄', '张三', '张三', '李四', '大黄', '张三', '张三', '李四'] names1 = [] for i in names: print(i not in names1) if i not in names1: names1.append(i) print(names1)
这里的 in 和 not in 为成员运算,可以翻译为“在”或者“不在“的意思,返回值为 True 或者 False 。
-
利用 for 判断元素在列表中的个数来进行去重
names = ['张三', '李四', '大黄', '张三', '张三', '李四', '大黄', '张三', '张三', '李四'] for i in range(len(names) - 1, -1, -1): if names.count(names[i]) > 1: del names[i] print(names)
这里我是直接给出正确的去重思路的,但是根据前文,我们学会了一种删除方法叫做 remove() 这种方法相比与 del ,只需要提供元素的值即可,但是我们不去使用他,因为使 用之后的代码如下:
names = ['张三', '李四', '大黄', '张三', '张三', '李四', '大黄', '张三', '张三', '李四']
for i in names:
if names.count(i) > 1:
names.remove(i)
print(names)
上面这种方法在运行的时候会存在很大弊端,即删不干净,究其原因是 当元素被删除时,后面的元素顶到前面来,位置发生了改变,但是对于 for 循环来说,下标还是按照之前1,2,3,4的路线走,所以就会直接转到被删除元素下下位元素,而缺失了中间隔着的原本应该到的元素,所以,我们应采取最上面的那种算法,避免这个问题。
生成列表最简单的方法——列表推导式
作用:更快的一次性生成有多个元素的列表
- 语法:[表达式 for 变量 in 容器]
list1 = [i for i in range(1, 11)]
print(list1)
- 带条件的列表推导式
语法:[ 表达式 for 变量 in 容器 if 条件 ]
list2 = [i for i in range(1, 11) if i % 2 != 0]
print(list2)
- 双重或多重循环
语法:[表达式 for 变量 in 容器]
list3 = [f'{x}*{y}={x * y}' for x in range(1, 10) for y in range(1, x + 1)]
print(list3)
最后一块比较简单了,我就直接拿的源码加注释,看起来也更加易懂,耗时两天,总算是把列表这一块搞完了,后面要开始说字符串了,麻了麻了,手要断了。
条件的列表推导式
语法:[ 表达式 for 变量 in 容器 if 条件 ]
list2 = [i for i in range(1, 11) if i % 2 != 0]
print(list2)
- 双重或多重循环
语法:[表达式 for 变量 in 容器]
list3 = [f'{x}*{y}={x * y}' for x in range(1, 10) for y in range(1, x + 1)]
print(list3)
最后一块比较简单了,我就直接拿的源码加注释,看起来也更加易懂,耗时两天,总算是把列表这一块搞完了,后面要开始说字符串了,麻了麻了,手要断了。