Python 基础合集4:Python的数据结构(str、list、tuple、dict、set)

一、前言

本节主要介绍几种数据结构(str、list、tuple、dict、set)及其应用(增删改查和注意事项)。

环境说明:Python 3或anaconda 3,使用编辑器 jupyter notebook(anaconda自带,Python自行安装),通过命令行或其他编辑器也可以。

二、Python的数据结构

2.1 序列类型结构:str、tuple、list

image.png
相同点:

  • 三者都有正负索引(有序序列),可以通过索引取值,支持循环遍历每个元素
  • 都支持切片
  • 都支持判断某元素是否在序列内(in/not in)

不同点:

  • str和tuple创建之后就不可修改,只支持查询,而list支持增删改查
  • str只能使用字符串,tuple和list支持任意数据类型
  • 内存存储,值相同的str 分别赋值给两个变量,两个变量的id一致,即值相同的str 分配到的存储空间是同一个,如果同一个变量前后赋值两次,两次的id不同,而tuple和list的上述两种情况的id都不同。判断空间是否一致可以使用val1 is val2,查看空间id使用id(val),判断值是否相等则使用val1 == val2
# 字符串
a = '1'
b = '1'
print(a == b)  # 结果为:True
print(a is b)  # 结果为:True
print(id(b))   # 结果为:23331617072
b = '2'
print(id(b))   # 结果为:23331774640

# tuple
a = 1,2
b = 1,2
print(a == b)  # 结果为:True
print(a is b)  # 结果为:False
print(id(b))   # 结果为:23361861568
b = 1,2,3
print(id(b))   # 结果为:23361862208

# list
a = [1,2]
b = [1,2]
print(a == b)  # 结果为:True
print(a is b)  # 结果为:False
print(id(b))   # 结果为:23362359168
b = [1,2,3]
print(id(b))   # 结果为:23362319488

2.1.1 查

两种取法:一个是取单个值,一个是取切片。
不同点:

  • 语法不同
    • 取单值的格式:【列表名[索引值]】
    • 取切片的格式:【列表名[左索引值 : 右索引值]】(中间用冒号进行隔开),取得的切片的数据类型还是列表。
  • 返回的对象可能不同
    • 取单值:字符串返回的还是字符串,元组和列表取值返回的是对应的元素,元素是什么数据类型返回的值也是对应的数据类型
    • 取切片:原变量是什么数据类型,返回的就是什么数据类型,即字符串切片返回的还是字符串,元组切片返回的还是元组,列表切片返回的还是列表。
# 针对以下前三行代码,分别保留一行不注释,查看运行结果,取数逻辑一致,返回形式根据原变量的类型会有些不同(不同点参考代码前文字说明)
val = '56789'
# val = (5,6,7,8,9)
# val = [5,6,7,8,9]
 
# 取值,没有冒号
print(val[2])        # 取出第2位
print(type(val[2]))  # str结果为<class 'str'>,tuple和list结果为:<class 'int'>
 
# 取切片,带冒号
# 左边空,取到第0位,从第0位开始,取n个元素。
print(val[0:2])     # 取出第0、1位
print(val[:2])      # 取出第0、1位
print(type(val[:2]))# tuple结果为:<class 'tuple'>,list结果为:<class 'list'>
 
# 右边空,表示从第m个元素开始取到尽头,即最后一位;
print(val[2:])      # 取出第2位到结束
 
# 冒号两边空,表示从第0位到最后一位,取整一个列表,相当于复制。
print(val[:])
print(val[0:5])
 
# 冒号左右都有数字([m,n])时,表示从第m个元素开始取,取到第(n-1)个。共取出(n-m)个元素。
print(val[1:3])    # 取出第1、2位
print(val[2:4])    # 取出第2、3位

切片小结:取法口诀:左取右不取,空则取到头。(假设n>m>0)
(1)[ :n],冒号左边空(或者为0),,表示从头,即第0位开始,取到第(n-1)个元素,共取n个元素;
(2)[m:],右边空,,表示从第m个元素开始取到尽头,即最后一位;
(3)[ : ],冒号两边空,,表示从第0位到最后一位,取整一个列表,相当于复制。
(4)[m : n],冒号左右都有数字时,,表示从第m个元素开始取,取到第(n-1)个。共取出(n-m)个元素。


取切片的时候,还有第3个参数,这个参数可以指定步数,即每几个取一次。默认步数是1,即每个元素都取。具体看看例子:

# 这里拿list示例,其他大同小异
val = [5,6,7,8,9]
print(val[0:5:1])  # 默认情况下,取出第0~4个元素,结果为:[5, 6, 7, 8, 9]
print(val[0:5:2])  # 步数改为2,每两个取一次,取第0、2、4元素,结果为[5, 7, 9]

2.1.2 增

增加元素只有列表支持。
使用的语法:**列表名.append() **或 列表名.extend()
二者区别:append() 增加一个元素,extend() 可增加多个元素。

ls = [5,6,7]
ls.append(8)
print(ls)    # 结果为:[5,6,7,8]
ls.extend([9,0])
print(ls)    # 结果为:[5,6,7,8,9,0]

append() 和 extend() 都是在列表末尾增加元素,如果是指定位置增加,可以使用该语法:列表名.insert(索引值, 新元素)

ls = [5,6,7]
ls.insert(1,4) # 第1位插入4,后面元素索引加1
print(ls)      # 结果为:[5, 4, 6, 7]
ls.insert(2,3) # 第2位插入3,后面元素索引加1
print(ls)      # 结果为:[5, 4, 3, 6, 7]

insert() 一次也只能插入一个元素,如果要一次性插入多个,可以通过循环或切片实现:

ls = [5,6,7]
insert_params = [3,4]         # 需要插入元素列表
begin_index = 1			      # 开始位置

# 方法:1:通过循环遍历
for i in insert_params:       # 遍历插入元素列表
    ls.insert(begin_index,i)  # 将值插入到指定的索引中
print(ls)                     # 结果为:[5, 4, 3, 6, 7]

# 方法2:通过列表拼接
ls = ls[:begin_index] + insert_params + ls[begin_index:]
print(ls)                     # 结果为:[5, 4, 3, 6, 7]

2.1.3 删

语法1:del 列表名[索引值] ,注意这里del后面是一个空格
语法2:列表名.remove([元素]),移除指定元素,如果元素重复出现多次,仅移除首次;
语法3:列表名.pop([索引值]),删除对应索引值的元素并返回,即又删又取。

ls = [5,6,7,6,5]
ls.remove(6)  # 移除元素6
print(ls)     # 结果为:[5, 7, 6, 5]
del ls[2]     # 删除索引2对应元素
print(ls)     # 结果为:[5, 7, 5]
ls.pop(-2)    # 删除倒数第二个元素,并返回该元素,即7
print(ls)     # 结果为:[5, 5]

2.1.4 改

修改元素只有列表具备这样的功能。修改元素包含替换值、排序等。

  • 修改语法:列表名[旧值的索引值]=新值
  • 排序
    • 语法1:列表名.sort(key,reverse),修改原列表,reverse是布尔值,False表示升序(默认),True表示降序。key支持自定义排序。
    • 语法2:sorted(列表名,key,reverse),返回新的列表。
ls = [5,6,7]
ls[1] = 8
print(ls)                  # 结果为:[5, 8, 7]
ls.sort()
print(ls)                  # 结果为:[5, 7, 8]
ls.sort(reverse=True)
print(ls)                  # 结果为:[8, 7, 5]
ls_new = sorted(ls)
ls_new                     # 结果为:[5, 7, 8]
print(ls)                  # 结果为:[8, 7, 5]

# 自定义排序,7->5->8,其他递增
ls = [8,7,1,5,7,0,3]
ls_new = []
num_ls = [7,5,8]                 # 将指定排序,按顺序放到列表中
for j in num_ls:                 # 遍历指定排序的元素
    for i in range(ls.count(j)): # 取每个元素重复次数进行循环
        ls_new.append(j)         # 将指定排序的元素添加到新列表
        ls.remove(j)             # 在原列表移除元素
ls_new = ls_new+sorted(ls)       # 将新列表和剩下排好序的列表拼接
print(ls_new)

2.2 映射类型结构:dict

特点:

  • 无序:集合内的元素没有顺序
  • 支持增删改查操作
  • 键值对:通过冒号关联键值对
  • 用{}声明
scores = {'小A': 95, '小B': 90}
# 查询
print(scores['小A']) # 结果为:95

# 删除
del scores['小B']
print(scores)        # 结果为:{'小A': 95}

# 新增
scores['小D'] = 100
print(scores)        # 结果为:{'小A': 95, '小D': 100}

# 修改
scores['小D'] = 99
print(scores)        # 结果为:{'小A': 95, '小D': 99}

d = {'小A': 95, '小C': 90}
scores.update(d)
print(scores)        # 结果为:{'小A': 95, '小D': 99, '小C': 90}

2.3 集合类型结构:set

特点:

  • 无序:集合内的元素没有顺序
  • 唯一:集合内的元素没有重复
  • 用 {} 声明:集合内的元素通过 {}括起来。注意在创建空集合,不能直接使用 val = {} ,默认是字典。应使用 val = set()
  • 可以对集合元素进行增删改
st = {1,2,3,3}
print(st)        # 结果为:{1, 2, 3}

# 增加元素
st.add(5)
print(st)        # 结果为:{1, 2, 3, 5}

# 更新元素
st.update([3,4,5])
print(st)        # 结果为:{1, 2, 3, 4, 5}

# 删除元素
st.remove(2)     # 删除元素,不存在会报错
print(st)        # 结果为:{1, 3, 4, 5}
st.discard(2)    # 删除元素,不存在不会报错,删除效果同remove()
print(st)        # 结果为:{1, 3, 4, 5}

st_1 = {1,3,6}
st_2 = {2,4,6}
# 交集
print(st_1 & st_2)   # 结果为:{6}
# 并集
print(st_1 | st_2)   # 结果为:{1, 2, 3, 4, 6}

三、小结

字符串列表元组字典集合
基本格式引号(单、双、三引号均可),如’A123’中括号[]、逗号分隔。
如[‘小明’,17,5.2]
小括号()、逗号分隔。如(‘小明’,17,5.2)大括号{}、冒号连接键和值、逗号分隔。
如{‘小明’:95,‘小红’:90,‘小刚’:90}
大括号{}、逗号分隔。
如{17, 5.2, ‘小明’}
取值字符串名[索引值]字符串名[索引值1:索引值2]
正向从0开始计算,反向从-1开始
列表名[索引值]列表名[索引值1:索引值2]
正向从0开始计算,反向从-1开始
元组名[索引值]元组名[索引值1:索引值2]
正向从0开始计算,反向从-1开始
字典名[键]\
增加元素\列表名.append(元素)列表名.extend(元素)\字典名[键] = 值集合名.add(元素)
修改元素\列表名[旧值的索引值]=新值列表名.sort()列表名.insert(索引值,元素)sorted(列表名,key,reverse)\字典名[键] = 新值(同新增元素)、
字典名.update(新字典)
集合名.update(集合/序列)
删除元素\del 列表名[元素的索引](空格隔开)列表名.remove(元素)列表名.pop(索引值)\del 字典名[键](空格隔开)集合名.remove(元素)集合名.discard(元素)

注意:所有的符号都是英文符号!

下节预告:条件与循环

  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Xin学数据

为你点亮一盏灯,愿你前进无阻。

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值