我的Python学习之路2
序列(sequence)
序列是Python中最基本的一种数据结构
数据结构指计算机中数据存储的方式
序列用于保存一组有序的数据,所有的数据在序列当中都有一个唯一的位置(索引)
并且序列中的数据会按照添加的顺序来分配索引
序列的分类:
- 可变序列(序列中的元素可以改变):
- 列表(list)
- 不可变序列(序列中的元素不能改变):
- 字符串(str)
- 元组(tuple)
一、列表(list)
列表是Python中的一个对象
对象(object)就是内存中专门用来存储数据的一块区域
之前我们学习的对象,像数值,它只能保存一个单一的数据
列表中可以保存多个有序的数据
列表是用来存储对象的对象
列表的使用:
1. 列表的创建
my_list = []
# 创建了一个空列表
列表存储的数据,我们称为元素
一个列表中可以存储多个元素,也可以在创建列表时,来指定列表中的元素
my_list = [10]
创建一个只包含一个元素的列表
当向列表中添加多个元素时,多个元素之间使用,隔开
my_list = [10,20,30,40,50]
创建了一个保护有5个元素的列表
print(my_list[::-3])
列表中可以保存任意的对象
my_list = [10,'hello',True,None,[1,2,3],print]
2. 操作列表中的数据
列表中的对象都会按照插入的顺序存储到列表中,
第一个插入的对象保存到第一个位置,第二个保存到第二个位置
我们可以通过索引(index)来获取列表中的元素
索引是元素在列表中的位置,列表中的每一个元素都有一个索引
索引是从0开始的整数,列表第一个位置索引为0,第二个位置索引为1,第三个位置索引为2,以此类推
2.1 通过索引获取列表中的元素
语法:my_list[索引] my_list[0]
如果使用的索引超过了最大的范围,会抛出异常IndexError: list index out of range
2.2 获取列表的长度,列表中元素的个数
len(my_list)
len()函数,通过该函数可以获取列表的长度
获取到的长度的值,是列表的最大索引 + 1
2.3 切片
切片指从现有列表中,获取一个子列表
创建一个列表,一般创建列表时,变量的名字会使用复数
stus = ['孙悟空','猪八戒','沙和尚','唐僧','蜘蛛精','白骨精']
列表的索引可以是负数
如果索引是负数,则从后向前获取元素,-1表示倒数第一个,-2表示倒数第二个 以此类推
stus[-2]
2.3.1 通过切片来获取指定的元素
语法:列表[起始:结束]
- 通过切片获取元素时,会包括起始位置的元素,不会包括结束位置的元素
- 做切片操作时,总会返回一个新的列表,不会影响原来的列表
- 起始和结束位置的索引都可以省略不写
- 如果省略结束位置,则会一直截取到最后
- 如果省略起始位置,则会从第一个元素开始截取
- 如果起始位置和结束位置全部省略,则相当于创建了一个列表的副本
print(stus[1:])
print(stus[:3])
print(stus[:])
print(stus)
语法:列表[起始:结束:步长]
-
步长表示,每次获取元素的间隔,默认值是1
切片输出样例.pngprint(stus[0:5:3])
-
步长不能是0,但是可以是负数
print(stus[::0]) ValueError: slice step cannot be zero
-
如果是负数,则会从列表的后部向前边取元素
print(stus[::-1])
3. 序列通用操作
-
+可以将两个列表拼接为一个列表
my_list = [1,2,3] + [4,5,6] -
* 可以将列表重复指定的次数
my_list = [1,2,3] * 5 -
in 和 not in
- in用来检查指定元素是否存在于列表中
- 如果存在,返回True,否则返回False
-
not in用来检查指定元素是否不在列表中
- 如果不在,返回True,否则返回False
-
len()获取列表中的元素的个数
-
min() 获取列表中的最小值
-
max() 获取列表中的最大值
-
两个方法(method),方法和函数基本上是一样,只不过方法必须通过 对象.方法() 的形式调用
xxx.print()
方法实际上就是和对象关系紧密的函数-
s.index()
获取指定元素在列表中的第一次出现时索引 -
index()
的第二个参数,表示查找的起始位置 , 第三个参数,表示查找的结束位置 - 如果要获取列表中没有的元素,会抛出异常
print(stus.index('牛魔王')) ValueError: '牛魔王' is not in list
- s.count() 统计指定元素在列表中出现的次数
print(stus.count('牛魔王'))
-
stus = ['孙悟空','猪八戒','沙和尚','唐僧','蜘蛛精','白骨精','沙和尚','沙和尚']
print('牛魔王' not in stus)
print('牛魔王' in stus)
arr = [10,1,2,5,100,77]
print(min(arr) , max(arr))
print(stus.index('沙和尚'))
print(stus.index('沙和尚',3,7))
print(stus.count('牛魔王'))
序列通用操作样例.png
4 修改列表中的元素
-
直接通过索引来修改元素
stus[0] = 'sunwukong'
-
通过del来删除元素
del stus[2]
删除索引为2的元素 -
通过切片来修改列表
- 在给切片进行赋值时,只能使用序列
stus[0:2] = ['牛魔王','红孩儿']
使用新的元素替换旧元素
stus[0:2] = ['牛魔王','红孩儿','二郎神']
stus[0:0] = ['牛魔王']
向索引为0的位置插入元素 - 当设置了步长时,序列中元素的个数必须和切片中元素的个数一致
stus[::2] = ['牛魔王','红孩儿','二郎神']
- 在给切片进行赋值时,只能使用序列
-
通过切片来删除元素
del stus[0:2]
del stus[::2]
stus[1:3] = []
以上操作,只适用于可变序列
s = 'hello'
s[1] = 'a' 不可变序列,无法通过索引来修改
可以通过 list()
函数将其他的序列转换为list
s = list(s)
stus = ['孙悟空','猪八戒','沙和尚','唐僧','蜘蛛精','白骨精']
print("修改前:",stus)
stus[0] = 'sunwukong'
print('修改后:',stus)
del stus[2]
print('修改后:',stus)
stus = ['孙悟空','猪八戒','沙和尚','唐僧','蜘蛛精','白骨精']
stus[0:2] = ['牛魔王','红孩儿']
print('修改后:',stus)
stus[0:2] = ['牛魔王','红孩儿','二郎神']
print('修改后:',stus)
stus[0:0] = ['牛魔王']
print('修改后:',stus)
stus = ['孙悟空','猪八戒','沙和尚','唐僧','蜘蛛精','白骨精']
stus[::2] = ['牛魔王','红孩儿','二郎神']
print('修改后:',stus)
s = 'hello'
s = list(s)
print(s)
修改元素样例.png
5. 列表的方法
列表的方法
-
append()
向列表的最后添加一个元素
stus.append('唐僧') -
insert()
向列表的指定位置插入一个元素- 参数:
1.要插入的位置
2.要插入的元素
stus.insert(2,'唐僧')
- 参数:
-
extend()
使用新的序列来扩展当前序列
需要一个序列作为参数,它会将该序列中的元素添加到当前列表中
stus.extend(['唐僧','白骨精'])
等价于stus += ['唐僧','白骨精']
-
clear()
清空序列stus.clear()
-
pop()
根据索引删除并返回被删除的元素
result = stus.pop(2)
删除索引为2的元素
result = stus.pop()
删除最后一个 -
remove()
删除指定值得元素,如果相同值得元素有多个,只会删除第一个
stus.remove('猪八戒')
-
reverse()
用来反转列表
stus.reverse()
-
sort()
用来对列表中的元素进行排序,默认是升序排列
如果需要降序排列,则需要传递一个reverse=True
作为参数
my_list = list('asnbdnbasdabd')
my_list = [10,1,20,3,4,5,0,-2]
my_list.sort(reverse=True)
6 遍历列表
指的就是将列表中的所有元素取出来
- 通过
while
循环来遍历列表
i = 0
while i < len(stus):
print(stus[i])
i += 1
- 通过for循环来遍历列表
语法:
for 变量 in 序列 :
代码块
for循环的代码块会执行多次,序列中有几个元素就会执行几次
没执行一次就会将序列中的一个元素赋值给变量,
所以我们可以通过变量,来获取列表中的元素
for s in stus :
print(s)
7. range()
函数
- 用来生成一个自然数的序列
r = range(5) # 生成一个这样的序列[0,1,2,3,4]
r = range(0,10,2)
r = range(10,0,-1)
-
该函数需要三个参数
- 1.起始位置(可以省略,默认是0)
- 2.结束位置
- 3.步长(可以省略,默认是1)
-
通过range()可以创建一个执行指定次数的for循环
for()循环除了创建方式以外,其余的都和while一样,
包括else、包括break continue都可以在for循环中使用
并且for循环使用也更加简单
for i in range(0,30,2):
print(i)
二、元组 tuple
元组是一个不可变的序列
它的操作的方式基本上和列表是一致的
所以你在操作元组时,就把元组当成是一个不可变的列表就ok了
一般当我们希望数据不改变时,就使用元组,其余情况都使用列表
1.创建元组
-
使用()来创建元组
my_tuple = ()
创建了一个空元组
print(my_tuple,type(my_tuple)) # <class 'tuple'>
my_tuple = (1,2,3,4,5)
创建了一个5个元素的元组 -
元组是不可变对象,不能尝试为元组中的元素重新赋值
my_tuple[3] = 10 TypeError: 'tuple' object does not support item assignment
-
当元组不是空元组时,括号可以省略
-
如果元组不是空元组,它里边至少要有一个,
my_tuple = 10,20,30,40
my_tuple = 40
此时便是一个整形 -
元组的解包(解构)
解包指就是将元组当中每一个元素都赋值给一个变量
my_tuple = 10 , 20 , 30 , 40
a,b,c,d = my_tuple
print("a =",a)
print("b =",b)
print("c =",c)
print("d =",d)
交互a 和 b的值,这时我们就可以利用元组的解包
a , b = b , a
print(a , b)
my_tuple = 10 , 20 , 30 , 40
在对一个元组进行解包时,变量的数量必须和元组中的元素的数量一致
也可以在变量前边添加一个*,这样变量将会获取元组中所有剩余的元素
a , b , *c = my_tuple
a , *b , c = my_tuple
*a , b , c = my_tuple
a , b , *c = [1,2,3,4,5,6,7]
a , b , *c = 'hello world'
- 不能同时出现两个或以上的*变量
*a , *b , c = my_tuple SyntaxError: two starred expressions in assignment
三、可变对象
-
每个对象中都保存了三个数据:
id(标识)
type(类型)
value(值)-
列表就是一个可变对象
a = [1,2,3]
-
a[0] = 10 (改对象)
- 这个操作是在通过变量去修改对象的值
- 这种操作不会改变变量所指向的对象
- 当我们去修改对象时,如果有其他变量也指向了该对象,则修改也会在其他的变量中体现
-
a = [4,5,6] (改变量)
- 这个操作是在给变量重新赋值
- 这种操作会改变变量所指向的对象
- 为一个变量重新赋值时,不会影响其他的变量
-
一般只有在为变量赋值时才是修改变量,其余的都是修改对象
-
四、字典(dict)
- 字典
- 字典属于一种新的数据结构,称为映射(mapping)
- 字典的作用和列表类似,都是用来存储对象的容器
- 列表存储数据的性能很好,但是查询数据的性能的很差
- 在字典中每一个元素都有一个唯一的名字,通过这个唯一的名字可以快速的查找到指定的元素
- 在查询元素时,字典的效率是非常快的
- 在字典中可以保存多个对象,每个对象都会有一个唯一的名字
这个唯一的名字,我们称其为键(key),通过key可以快速的查询value
这个对象,我们称其为值(value)
所以字典,我们也称为叫做键值对(key-value)结构
每个字典中都可以有多个键值对,而每一个键值对我们称其为一项(item)
五、集合(set)
- 集合和列表非常相似
- 不同点:
1.集合中只能存储不可变对象
2.集合中存储的对象是无序(不是按照元素的插入顺序保存)
3.集合中不能出现重复的元素
- 不同点: