返回笔记列表
01 · NOTES / Python

数据容器

2026 年 1 月 15 日

数据容器

分类:Python

最后修改时间:2026-01-15 14:42:32.024


集合

集合是一种:无序元素唯一的容器类型。 集合分为两种,分别是:

  1. 可变集合(set):内部的元素无序(不保证顺序)、不能通过下标访问元素、会自动去除重复元素。
  2. 不可变集合(forzenset):特点和可变集合一样,唯一的区别就是:其中的元素不可修改。

定义集合

  1. 可变集合的定义方式:使用花括号{}包裹,不同的数据项之间,用,做分隔。
# 定义有内容的【可变集合】
s1 = {10, 20, 20, 30, 40, 40, 50, 60, 60, 70, 80, 90, 100}
s2 = {'你好', 'hello', '你好', 'atguigu', '北京'}
s3 = {10, '你好', True, 1, 12.4}
print(type(s1), s1)  # <class 'set'> {100, 70, 40, 10, 80, 50, 20, 90, 60, 30}
print(type(s2), s2)  # <class 'set'> {'atguigu', 'hello', '你好', '北京'}
print(type(s3), s3)  # <class 'set'> {True, 10, '你好', 12.4}

# 定义空集合(可变集合)
s1 = set()
print(type(s1), s1)  # <class 'set'> set()
**注意:**不能直接写\{\}来定义空集合,因为直接写\{\}定义的是:空字典。
  1. 不可变集合的定义方式:借助内置的forzenset函数。
# 定义有内容的【不可变集合】
s1 = frozenset({10, 20, 20, 30, 40, 40, 50, 60, 60, 70, 80, 90, 100})
s2 = frozenset({'你好', 'hello', '你好', 'atguigu', '北京'})
s3 = frozenset({10, '你好', True, 1, 12.4})
print(type(s1), s1)
print(type(s2), s2)
print(type(s3), s3)

# frozenset 接收的参数,可以是任意可迭代对象,但最终返回的一定是【不可变集合】
s1 = frozenset([10, 20, 30, 40, 50])
s2 = frozenset((10, 20, 30, 40, 50))
s3 = frozenset('hello')
print(type(s1), s1)
print(type(s2), s2)
print(type(s3), s3)

# 定义空集合(不可变集合)
s3 = frozenset()
print(type(s3), s3)

集合中不能嵌套【可变集合】,但可以嵌套【不可变集合】

只有不可变的东西才能放入集合

增删改查

# add方法:向集合中添加元素
s1 = {10, 20, 30, 40, 50}
s1.add(60)
print(s1)

# update方法:向集合中添加元素(必须传递可迭代对象,例如:列表、元组、集合等)
s1 = {10, 20, 30, 40, 50}
s1.update([60, 70])
s1.update((80, 90))
s1.update({100, 200})
s1.update(range(300, 308))
print(s1)
# remove方法:从集合中移除元素(移除不存在的元素,会报错)
s1 = {10, 20, 30, 40, 50}
s1.remove(20)
print(s1)

# discard方法:从集合中移除元素(移除不存在的元素,不会报错)
s1 = {10, 20, 30, 40, 50}
s1.discard(80)
print(s1)

# pop方法:从集合中移除一个任意元素,返回值是移除的那个元素
s1 = {10, 20, 30, 40, 50}
s2 = {'你好', '北京', '尚硅谷', 'hello'}
result = s1.pop()
print(s1)
print(result)

# clear方法:清空集合
s1 = {10, 20, 30, 40, 50}
s1.clear()
print(s1)

  1. **注意:**集合没有下标,也不支持replace方法,所以集合没有专门用于“改”的方法,但可以使用:remove+add的组合,来达到“修改”的效果。

# 改
# 使用 add + remove 的组合,来实现修改的效果
s1 = {10, 20, 30, 40, 50}
s1.remove(20)
s1.add(66)
print(s1)
  1. **注意:**由于集合没有下标,也不支持切片操作,所以集合不具备按位置访问的能力。虽然不能通过下标读取元素,但可以使用【成员运算符】来判断:某个元素是否在集合中

# 查:集合不能通过下标去读取元素,但能通过 【成员运算符】去查看集合中是否包含指定元素
# 由于成员运算符适用于所有数据容器,所以我们会等所有数据容器都讲完以后,再说成员运算符
s1 = {10, 20, 30, 40, 50}
# s1[0] # 此行报错,因为集合不能通过下标访问元素

# 先提前感受一下成员运算符
result = 20 not in s1
print(result)

常用方法

  1. 使用集合A.difference(集合B),找出集合A中,不同于集合B的元素。
# 集合A.difference(集合B):
# 作用:找出集合A中,不同于集合B的元素(集合A 与 集合B 都不变,返回的是一个新的集合)
s1 = {10, 20, 30, 40, 50}
s2 = {30, 40, 50, 60, 70}
result = s1.difference(s2)
print(s1)
print(s2)
print(result)
  1. 使用集合A.difference_update(集合B),从集合A中,删除集合B中存在的元素。3
# 集合A.difference_update(集合B):
# 作用:从集合A中,删除集合B中存在的元素(集合A会被修改,集合B不会)
s1 = {10, 20, 30, 40, 50}
s2 = {30, 40, 50, 60, 70}
s1.difference_update(s2)
print(s1)
print(s2)
  1. 使用集合A.union(集合B),合并两个集合,集合A 和 集合B 都不变,返回的是一个新的集合。
# 集合A.union(集合B):
# 作用:合并两个集合,集合A 和 集合B 都不变,返回的是一个新的集合
s1 = {10, 20, 30, 40, 50}
s2 = {30, 40, 50, 60, 70}
result = s2.union(s1)
print(s1)
print(s2)
print(result)
  1. 使用集合A.issubset(集合B),判断集合A是否为集合B的子集,返回值为布尔值。
# 集合A.issubset(集合B):
# 作用:判断集合A是否为集合B的子集
# 如果 集合A的所有元素都在集合B中,那就返回True,否则返回False
s1 = {10, 20, 30, 40, 50}
s2 = {30, 40, 50, 60, 70}
s3 = {30, 40, 50}
result = s3.issubset(s1)
print(result)
  1. 使用集合A.issuperset(集合B),判断集合A是否是集合B的超集,返回值为布尔值。
# 集合A.issuperset(集合B):
# 作用:判断集合A是否是集合B的超集
# 如果集合A中,包含了集合B中的所有元素,那就返回True,否则返回False
s1 = {10, 20, 30, 40, 50}
s2 = {30, 40, 50, 60, 70}
s3 = {30, 40, 50}
result = s1.issuperset(s3)
print(result)
  1. 使用集合A.isdisjoint(集合B),判断集合A和集合B是否没有交集,返回值为布尔值。
# 集合A.isdisjoint(集合B):
# 作用:
# 如果没有交集,返回True;只要有一个公共元素,就返回False
s1 = {10, 20, 30, 40, 50}
s2 = {30, 40, 50, 60, 70}
s3 = {80, 90}
result = s1.isdisjoint(s2)
print(result)

数学运算

s1 = {10, 20, 30, 40, 50, 60}
s2 = {40, 50, 60, 70, 80, 90}

# 并集
result = s1 | s2
print(result)

# 交集
result = s1 & s2
print(result)

# 差集
result = s1 - s2
print(result)

# 对称差集
result = s1 ^ s2
print(result)

循环遍历

由于集合不支持下标,所以集合不能使用 while 循环遍历。

s1 = {10, 20, 30, 40, 50, 60}

# 集合不能使用while循环遍历(以下是错误示例)
# index = 0
# while index < len(s1):
#     print(s1[index])
#     index += 1

# 集合可以使用for循环遍历
for item in s1:
    print(item)

集合特点总结

  1. 无序:集合中的元素没有固定顺序,无法通过下标访问。
  2. 不重复:集合会自动去重,同一个元素只会保留一份。
  3. 分为两种:可变集合合(set)和不可变集合(forzenset)。
  4. 集合中的元素必须是不可变类型(如:数字、字符串、元组)。
  5. 集合支持:并集、交集、差集、对称差集等数学操作。 **一句话总结:**集合是可以去重的数据容器,当只关心元素是否存在,而不在乎顺序的时,首选集合。

列表

增删改查

列表(list) 的核心操作:

  • 新增(Create)
  • 查询(Read)
  • 修改(Update)
  • 删除(Delete)

定义列表

#定义有内容的列表
list1=[43,523,53,35,23]
list2=['awe','eWAD','sdas','哇哇哇']
list3=[23.,4325,563,'wddas']
list4=[24,52,21,'wdasds',[23,5,4,'2wse']]

#定义空列表(列表中的数据后期通过特定语法填充)
list5=[]
list6=list()
print(list1,type(list1))
print(list2,type(list2))
print(list3,type(list3))
print(list4,type(list4))
print(list5,type(list5))
print(list6,type(list6))
  • 列表中的元素可以是不同数据类型
  • 列表可以嵌套列表
  • 空列表:[]list()

常用方法

#使用 sort 方法,对列表排序(默认从小到大),若想从大到小,可以将 reverse 参数设为True。
#若列表中的元素:都是数字,则按照数字的大小顺序进行排序。
nums=[23,11,32,30,17]
nums.sort(reverse=True)
print(nums)

#若列表中的元素:既有数字,又有字符串那就会报错。
# nums=[23,11,32,30,17,'尚硅谷']
# nums.sort()

#若列表中的元素:都是字符串,则按照字符串的 Unicode 编码大小进行排序
#所有的列表方法,都只作用于"当前层"的元素(浅层操作),不会自动进入嵌套的"里层"结构中。

元组

空元组

t1 = ()
t2 = tuple()

只有一个元素的元组

t1 = ('你好',)
t2 = (18,)
#如果不加","就是字符串

#实际开发中的元组,不一定是我们自己定义的,比如函数的可变参数*args就是一个元组
def demo(*args):1个用法
	return sum(args)
result = demo(100, 200, 300)
print(result)     #600

元组特点

函数解包列表或元组传参

#定义函数时,使用*args(变量不一定非要用args,比如写:*data也可以),将收到的多个参数,打包成一个元组
def test(*args):
    print(f'我是test函数,我收到的参数是{args},参数类型是{type(args)}')

list1=[100,200,300,400]
tuple1=('hello','你好','123')

#调用函数,传入列表/元组
# test(list1)
# test(tuple1)

#函数调用时,使用*对 列表/元组进行解包后,再传递参数
test(*list1)  #相当于写了test(100,200,300,400)
test(*tuple1)  #相当于写了test('hello','你好','123')

字典

**字典:**用来存放一组『键值对』数据,可通过『键(key)』对『值(value)』进行:增、删、改、查操作。

定义字典

用大括号 { } 包裹,每个元素之间用逗号,分隔,每个元素的格式为key:value 注意:字典中的 key 不能重复,若出现重复,则后写的会覆盖之前写的。

# 定义有内容的字典
d1 = {'张三': 72, '李四': 60, '王五': 85}
print(type(d1), d1)

# 定义空字典
d1 = {}
d2 = dict()
print(type(d1), d1)
print(type(d2), d2)

字典中的 key 必须是不可变类型,但 value 可以是任意类型。

# 字典中的key必须是不可变类型,但value可以是任意类型
# 通俗理解:只有不可变的东西,才能作为key
d1 = {250: 72, '李四': 60, '王五': 85}
d2 = {('抽烟', '喝酒'): 72, '李四': 60, '王五': 85}
# print(d1)
# print(d2)

# 错误示例:将列表作为key,是不行的
# d2 = {['抽烟', '喝酒']: 72, '李四': 60, '王五': 85}

字典可以嵌套

# 字典可以嵌套
student_dict = {
    2025001: {
        '姓名': '张三',
        '年龄': 18,
        '成绩': 72,
        '爱好': ['抽烟', '喝酒', '烫头']
    },
    2025002: {
        '姓名': '李四',
        '年龄': 19,
        '成绩': 60,
        '爱好': ['唱歌', '跳舞', '打台球']
    },
    2025003: {
        '姓名': '王五',
        '年龄': 20,
        '成绩': 85,
        '爱好': ['学习', '看书', '打太极']
    }
}
print(student_dict)

字典的增删改查

新增

新增语法:字典[key] = 值

# 新增
d1 = {'张三': 72, '李四': 60, '王五': 85}
d1['赵六'] = 100
print(d1)

删除

# 删除
d1 = {'张三': 72, '李四': 60, '王五': 85}

# 删除指定key所对应的那组键值对
del d1['张三']
print(d1)

# 删除指定key所对应的那组键值对,并返回这个key所对应的值
result = d1.pop('张三')
print(d1)
print(result)

# pop方法可以设置默认值
# 默认值可以保证:当要删除的key不存在的情况下,程序不会报错,并且返回这个默认值
result = d1.pop('奥特曼', '删除失败!')
print(d1)
print(result)

# 清空字典
d1.clear()
print(d1)

修改

d1 = {'张三': 72, '李四': 60, '王五': 85}

# 修改的写法,与新增的写法一样,若字典中有对应的key,就是修改;若没有,就是新增
d1['张三'] = 97
print(d1)

# 批量修改
d1.update({'李四': 40, '王五': 67})
print(d1)

查询

# 查询
d1 = {'张三': 72, '李四': 60, '王五': 85}

# 直接取值,若键(key)不存在,会报错
result = d1['张三']

# 安全取值,若键(key)不存在,会返回默认值(若没有设置默认值,则会返回None)
result = d1.get('奥特曼', '抱歉,key不存在!')
print(result)

常用方法

  • 使用keys方法,获取字典中所有的键
# keys方法:用于获取字典中所有的键
d1 = {'张三': 72, '李四': 60, '王五': 85}

# keys方法的返回值不是list,而是一种叫做dict_keys的类型
result = d1.keys()
print(result)
print(type(result))

# dict_keys和列表类似,可以被遍历,但要注意的是:它不能通过下标访问元素
for item in result:
    print(item)
print(result[0])

# 借助内置的list函数,可以将dict_keys转换成list
l1 = list(result)
print(l1)
print(type(l1))
  • 使用values方法,获取字典中所有的值。
# values方法:获取字典中所有的值
d1 = {'张三': 72, '李四': 60, '王五': 85}
# values方法的返回值类型是:dict_values,它的特点和dict_keys一样
result = d1.values()
print(result)
print(type(result))
  • 使用items方法,获取字典中所有的键值对(每组键值对以元组的形式呈现)
# items方法:获取字典中所有的键值对(每组键值对以元组的形式呈现)
d1 = {'张三': 72, '李四': 60, '王五': 85}

# items方法返回的类型是:dict_items,它的特点也和dict_keys一样
result = d1.items()
print(result)
print(type(result))

字典的循环遍历

字典不能使用while循环遍历,但可以使用for循环遍历

# 字典不能使用while循环遍历,但可以使用for循环遍历
d1 = {'张三': 72, '李四': 60, '王五': 85}

for key in d1:
    print(f'{key}的成绩是{d1[key]}')

for key in d1.keys():
    print(f'{key}的成绩是{d1[key]}')

字典总结

  1. 键值对结构:字典中的数据以key:value的形式存在,每个键都对应一个值。
  2. 键唯一:字典中的键(key)不能重复,若重复则后写的会覆盖前写的。
  3. 键不可变::键必须是不可变类型(如数字、字符串、元组等),而值可以是任意类型。
  4. 不支持下标:字典中的元素不能通过下标取值。
  5. 支持增删改查,支持for循环遍历。 一句话总结:字典是一种以“键”找“值”的映射型容器,当需要唯一标识 → 对应信息的结构时,首选字典。

字符串

字符串特点

  1. 字符串和列表、元组一样,也支持下标
  2. 字符串不可修改,不可嵌套

字符串常用方法

  1. 使用字符串.index(字符),获取『指定字符』在字符串中『第一次』出现的下标,返回值:下标。
msg = 'welcome to atguigu'
result = msg.index('t')
print(result)  # 8
  1. 使用字符串.split(字符),将字符串按照『指定字符』进行分隔,返回值:列表。
msg  = '尚硅谷@atguigu@你好'
result = msg.split('@')
print(result)  # ['尚硅谷', 'atguigu', '你好']
  1. 使用字符串.replace(字符串片段),将字符串中的某个字符串片段,替换成目标字符串,不会修改原字符串,返回新字符串。
msg = 'welcome to atguigu'
result = msg.replace('atguigu', '尚硅谷')
print(msg)    # welcome to atguigu
print(result) # welcome to 尚硅谷
  1. 使用字符串.count(字符),统计『指定字符』在字符串中出现的次数。
msg = 'welcome to atguigu'
result = msg.count('g')
print(result)  # 2
  1. 使用字符串.strip(),从某个字符串中删除指定字符串中的任意字符,不会修改原字符串,返回值:新字符串。(常用于去除字符串两端的空格
msg = '34215尚12硅34谷4132'
result = msg.strip('5432')
print(result)# 15尚12硅34谷41
#去除字符串两遍的空格
msg = '  尚硅谷  '
result = msg.strip()
print(result)# 尚硅谷

字符串常用内置函数

字符串也可以使用:max、min、len、sorted、sum函数,但实际开发中len函数最常用。

msg = 'welcome to atguigu'
result = len(msg)
print(result) # 18

序列

序列的切片与运算

序列:能连续存放元素的数据容器,而且元素有先后顺序,而且可以通过下标访问,所以:列表、元组、字符串,都是序列切片:从序列中按照指定范围,取出一部分元素,形成一个新的序列的操作。

语法格式

序列[起始索引:结束索引:步长]

  1. 切片操作的区间是左闭右开的,即:截取时包含起始位置,但不包含结束位置。步长是指取出元素时的间隔。
  2. 起始索引默认值为 0,结束索引默认截取到末尾,步长默认值为 1。
  3. 步长是指取出元素时的间隔
  4. 当起始索引大于结束索引时,步长必须为负数,否则结果是空列表。
  5. **序列相加: **把两个序列拼接在一起。 **注意:**只有同类型的序列才能相加(字符串+字符串、列表+列表、元组+元组)
list1 = [10, 20, 30, 40]
list2 = [50, 60, 70, 80]
list3 = list1 + list2
print(list3)  # [10, 20, 30, 40, 50, 60, 70, 80]
  1. **序列相乘(重复):**把序列重复指定的次数。
list1 = [10, 20, 30, 40]
list2 = list1 * 3
print(list2)  # [10, 20, 30, 40, 10, 20, 30, 40, 10, 20, 30, 40]

通用操作

除了上述这些内置函数以外,数据容器都可以进行如下通用操作

  • list函数:1.定义空列表;2.将【可迭代对象】转换为列表。
  • tuple函数:1.定义空元组;2.将【可迭代对象】转换为元组。
  • set函数:1.定义空集合;2.将【可迭代对象】转换为集合。
  • str函数:1.定义空字符串;2.将【任意类型】转换为字符串。
  • dict函数:1.定义空字典;2.将【可迭代对象】转换为字典。
  • 所有的数据容器,都支持【成员运算符】 in / not in 作用:判断某个元素是否在于容器中。
# list 函数:1.定义空列表。2.将【可迭代对象】转换为列表
res1 = list(range(8))
res2 = list('欢迎来到尚硅谷')
res3 = list({10, 20, 30, 40, 50})

# tuple 函数
res1 = tuple(range(8))

# set 函数
res1 = set(range(8))

# str 函数
res1 = str(range(8))

# dict 函数:交给dict函数的内容必须是键值对才可以
res2 = dict([('张三', 75), ('李四', 60), ('王五', 85)])

# 成员运算符:in / not in
hobby = ['抽烟', '喝酒', '烫头']
print('喝酒' not in hobby)
print(20 not in (10, 20, 30, 40, 50))
print('hel' not in 'hello,atgiugu')
print('上海' not in {'北京', '天津', '上海', '重庆'})
print('李华' not in {'张三': 75, '李四': 60})


TAGSpython