数据容器.集合
集合的特性
唯一(不重复)、无序、不变(非数学)
- 唯一性:集合中的元素不能重复
- 无序性:相同元素构成的多个集合中若元素位置不同则都是同一个集合
- 字典也具有无序性
- 意味着元素没有位置⇒没有indx⇒不支持与位置相关的操作:索引、切片等
- 不变性:集合中的元素(对象)必须是不可变类型(数值、字符串、tuple)
例:关于无序性的一种体现,本例中即使传入了有序的列表但依旧生成了无序的集合
set_1 = {i**2 for i in range(1,13) if i%2==0}
sortlist_1 = sorted(set_1)
print(sortlist_1)
sortset_1 = set(sortlist_1)
print(sortset_1)
[4, 16, 36, 64, 100, 144]
{64, 100, 4, 36, 16, 144}
集合的类型
- 可修改型set
- 不可修改型集合frozenset
- set——可变类型集合(支持增删改)
- 集合的创建
- 创建非空集合:set_1 = {元素}
- 创建空集合:set_1 = set( )
- set(序列) 返回由序列生成的相应元素的集合
- 注:{ }只能创建非空集合,创建空集合只能通过set()函数实现
- 集合的创建
set_1 = set()
print(f"set_1 class is : {type(set_1)}")
set_2 = {}
print(f"set_2 class is : {type(set_2)}")
set_1 class is : <class 'set'>
set_2 class is : <class 'dict'>
- frozenset 不可变类型(增删改)
- 可作为其他集合的元素(集合也可以嵌套)
集合推导式
集合 = {表达式 for 遍历可迭代对象获得的临时变量 in 迭代对象 if 条件语句}
- 含义:可迭代对象中的变量依次取出 并且 仅当条件语句为True时 才 求解表达式 将求解结果放入集合
- 例:求1~5中被2整除的数值的平方:
set_1 = {i**2 for i in range(1,6) if i%2==0}
print(set_1)
{16, 4}
增长集合
- 目标集合.add(添加的数据):添加一个数据
- 目标集合.update(可迭代对象):将可迭代对象中目标集合没有的元素添加进去
- 注:由于集合的不可变性——集合的对象都是不可变元素,所以增长集合的方法给出的集合的元素都要是不可变类型
缩减集合
- remove(元素)
- discard(元素)
- 注:二者的不同在于:
- 当集合中元素不在集合中时,remove会报错
- discard不论所删除的元素是否在集合中都会返回None,只不过当元素在集合中会删除,当元素不在集合中无法删除
- .pop() 删除任意一个元素
- 由于集合是无序的因此你无法预测/指定删除哪一个
- pop()可以用于遍历一个集合的所有元素
- .clear() :清空集合
#1.使用remove删除的元素不在集合中:
set_1 = {1,2,3}
set_1.remove(1024)
print(set_1)
---------------------------------------------------------------------------
KeyError Traceback (most recent call last)
Input In [25], in <cell line: 4>()
1 #1.使用remove删除的元素不在集合中:
2 set_1 = {1,2,3}
----> 4 set_1.remove(1024)
5 print(set_1)
KeyError: 1024
#2.使用discard删除的元素不在集合中:
set_1 = {1,2,3}
set_1.discard(1024)
print(set_1)
return_val = set_1.discard(1)
print(return_val) #不论是否成功删除,discard都是返回None
print(set_1)
{1, 2, 3}
None
{2, 3}
访问集合中的元素
- in 判断元素是否在集合中
- .pop() 删除元素并返回其的值
- 迭代循环:for a in set_1
集合的运算
-
运算后生成新集合
|运算|运算符|新集合方法|更新原集合方法|
|—|—|—|—|
|并| a|b |union|update|
|交| a&b |intersection|intersection_update|
|差| a-b |difference | difference_update|
|对称差(将公共元素去掉)|a^b|symmetric_difference|symmetric_difference_update| -
集合关系的判定
- 两集合交集是否为空判定:
- 语法:集合1.isdisjoint(集合2)
- 若两集合存在交集⇒返回True,若没有交集⇒返回Flase
- 两集合关系判定:
集合关系 运算符 例 子集 <= set1 <= set2#set1是set2的子集吗 真子集 < set1 < set2#set1是set2的真子集吗 相等 == set1 == set2#set1和set2是否相等 超集 >= set1 >= set2#set1是set2的超集吗 真超集 > set1 > set2#set1是set2的真超集吗
集合的应用
- 快速的去重复的数据项
- 判断一个元素是否在数据集中,如果这些数据的次序不重要,使用集合能够获得比列表更好的性能
集合的应用
- 快速的去重复的数据项
- 判断一个元素是否在数据集中,如果这些数据的次序不重要,使用集合能够获得比列表更好的性能
赋值的本质
-
对于类型,赋值会引用(指向)同一数据
-
多个变量通过赋值指向同一可变数据对象,任一变量对可变数据对象进行修改,其余变量引用的同一个数据也会一起发生改变
a = [1,2,3]
c = a #c和a指向了同一个[1,2,3]
b = [1,2,3] #在内存中创建了一个新的数据对象[1,2,3]和a指向的[1,2,3]不是同一个
a[2] = 10
print(a)
print(c)
print(b)
[1, 2, 10]
[1, 2, 10]
[1, 2, 3]
- 对于不可变数据对象,赋值会产生什么呢?
a = 12
c = 12
b = a
a = 12.4
print(a)
print(b)#b依旧是12
print(c)#c的12不是a的12
12.4
12
12
字符串大小写方法 是否改变原字符串的值? ---- 不会
str_1 = "this is my"
print(str_1)
upstr_1 = str_1.upper()
print(upstr_1)
this is my
THIS IS MY
关于len()和min()max()函数的参数类型是否为可迭代对象:
- 可迭代对象包括所有的数据容器:list dict tuple str set
list_1 = [1,2,3,4]
dic_1 = {1:'abc',2:'def'}
tuple_1 = (1,2,3,4,5)
str_1 = "this is arm"
set_1 = {1,2,3}
all_iterable = (list_1,dic_1,tuple_1,str_1,set_1)
for iterable in all_iterable:
print(f"{type(iterable)}len:{len(iterable)}",end='\t')
print()
for iterable in all_iterable:
print(f"{type(iterable)}min:{min(iterable)}",end = '\t')
<class 'list'>len:4 <class 'dict'>len:2 <class 'tuple'>len:5 <class 'str'>len:11 <class 'set'>len:3
<class 'list'>min:1 <class 'dict'>min:1 <class 'tuple'>min:1 <class 'str'>min: <class 'set'>min:1
验证:list1.extend(iterable) ⇔ for i in iterable: list1 += i ---- 是
list_1 = [1,2,3]
dict_1 = {9:'a',8:'b',7:'c'}
list_1.extend(dict_1)
print(list_1)
[1, 2, 3, 9, 8, 7]
list_2 = [10,11,12]
dic_2 = {'d':12,'b':13,'e':14}
for i in dic_2:
list_2 += i
print(list_2)
[10, 11, 12, 'd', 'b', 'e']
验证List.copy()方法是否只是引用型复制----是
l = [[1,2],[3,4]]
c = l.copy()
c[0][0]= 0
print(l)
#-使用copy方法复制l列表赋值给c, 修改c[0][1] l列表同样产生了变化,说明.copy()方法是引用型复制
[[0, 2], [3, 4]]
列表的排序方法: 列表.sort(key=None ,reverse=False)
- key传入函数,重新定义排序规则
name = ["Davi","Agluely","ise","ChenyuGuo"]
name.sort(lambda strs:len(strs),None)
print(name)
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
Input In [61], in <cell line: 2>()
1 name = ["Davi","Agluely","ise","ChenyuGuo"]
----> 2 name.sort(lambda strs:len(strs),None)
3 print(name)
TypeError: sort() takes no positional arguments
name = ["Davi","Agluely","ise","ChenyuGuo"]
name.sort(key = lambda strs:len(strs))
print(name)
['ise', 'Davi', 'Agluely', 'ChenyuGuo']
- ★注:指定参数的函数调用要写出函数定义的参数名,否则将会报错,此处为关键字参数,而采用位置参数将会报错,保险起见都采用关键字参数
- sort()排序是稳定排序
如何用sort实现多个条件的排序?
- 例: 先根据姓名长度进行排序; 对于具有相同姓名长度的再根据字符顺序进行排序?
- 答:返回一个二元组,可通过元组或者列表接受,二元组的内容为(字符长度,字符)
name = ["gllu","steven","hallye","klom","srae","samm"]
name.sort(key = lambda tuple_len_str : (tuple_len_str,len(tuple_len_str)))
print(name)
['gllu', 'hallye', 'klom', 'samm', 'srae', 'steven']
条件表达式
- 语法: 条件成立表达式 if 条件 else 条件不成立表达式
- p49 例4-5
vip_sort = int(input())
price = int(input())
print(price*0.97 if vip_sort == 0 else price*0.88)
0
100
97.0
骑车t = 50s + x / 3m/s
步行t = x / 1.2m/s
x = float(input("请输入距离(单位m)"))
t1 = 50 + x/3
t2 = x/1.2
if(t1 == t2):
print("一样快")
else:
print("骑车快" if t1<t2 else "步行快")
请输入距离(单位m)100
一样快
字典的key值可以是布尔类型吗
- 猜测:可以,因为布尔类型属于数值类型
dict_1 = {True:"123",False:"456",True:"789",True:"101112"}
print(dict_1[True])
dict_2 = {1:"1234",1:"5678",0:111,0:222}
print(dict_2[1])
101112
5678
批量添加数据项
new_dict = dict.fromkeys(iterable, default_value) 用于创建新字典
- iterable参数为可迭代对象,其元素作为新字典的键
- default_value是初始化的值,默认为None
dict_1 = dict.fromkeys(("key_1","key_2"))
print(dict_1)
{'key_1': None, 'key_2': None}
字典的元素要求
- 键:不可变元素(str/tuple/num)
- 值:任意类型
赋值的本质
-
对于类型,赋值会引用(指向)同一数据
-
多个变量通过赋值指向同一可变数据对象,任一变量对可变数据对象进行修改,其余变量引用的同一个数据也会一起发生改变
a = [1,2,3]
c = a #c和a指向了同一个[1,2,3]
b = [1,2,3] #在内存中创建了一个新的数据对象[1,2,3]和a指向的[1,2,3]不是同一个
a[2] = 10
print(a)
print(c)
print(b)
[1, 2, 10]
[1, 2, 10]
[1, 2, 3]
- 对于不可变数据对象,赋值会产生什么呢?
a = 12
c = 12
b = a
a = 12.4
print(a)
print(b)#b依旧是12
print(c)#c的12不是a的12
12.4
12
12
字符串大小写方法 是否改变原字符串的值? ---- 不会
str_1 = "this is my"
print(str_1)
upstr_1 = str_1.upper()
print(upstr_1)
this is my
THIS IS MY
关于len()和min()max()函数的参数类型是否为可迭代对象:
- 可迭代对象包括所有的数据容器:list dict tuple str set
list_1 = [1,2,3,4]
dic_1 = {1:'abc',2:'def'}
tuple_1 = (1,2,3,4,5)
str_1 = "this is arm"
set_1 = {1,2,3}
all_iterable = (list_1,dic_1,tuple_1,str_1,set_1)
for iterable in all_iterable:
print(f"{type(iterable)}len:{len(iterable)}",end='\t')
print()
for iterable in all_iterable:
print(f"{type(iterable)}min:{min(iterable)}",end = '\t')
<class 'list'>len:4 <class 'dict'>len:2 <class 'tuple'>len:5 <class 'str'>len:11 <class 'set'>len:3
<class 'list'>min:1 <class 'dict'>min:1 <class 'tuple'>min:1 <class 'str'>min: <class 'set'>min:1
验证:list1.extend(iterable) ⇔ for i in iterable: list1 += i ---- 是
list_1 = [1,2,3]
dict_1 = {9:'a',8:'b',7:'c'}
list_1.extend(dict_1)
print(list_1)
[1, 2, 3, 9, 8, 7]
list_2 = [10,11,12]
dic_2 = {'d':12,'b':13,'e':14}
for i in dic_2:
list_2 += i
print(list_2)
[10, 11, 12, 'd', 'b', 'e']
验证List.copy()方法是否只是引用型复制----是
l = [[1,2],[3,4]]
c = l.copy()
c[0][0]= 0
print(l)
#-使用copy方法复制l列表赋值给c, 修改c[0][1] l列表同样产生了变化,说明.copy()方法是引用型复制
[[0, 2], [3, 4]]
列表的排序方法: 列表.sort(key=None ,reverse=False)
- key传入函数,重新定义排序规则
name = ["Davi","Agluely","ise","ChenyuGuo"]
name.sort(lambda strs:len(strs),None)
print(name)
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
Input In [61], in <cell line: 2>()
1 name = ["Davi","Agluely","ise","ChenyuGuo"]
----> 2 name.sort(lambda strs:len(strs),None)
3 print(name)
TypeError: sort() takes no positional arguments
name = ["Davi","Agluely","ise","ChenyuGuo"]
name.sort(key = lambda strs:len(strs))
print(name)
['ise', 'Davi', 'Agluely', 'ChenyuGuo']
- ★注:指定参数的函数调用要写出函数定义的参数名,否则将会报错,此处为关键字参数,而采用位置参数将会报错,保险起见都采用关键字参数
- sort()排序是稳定排序
如何用sort实现多个条件的排序?
- 例: 先根据姓名长度进行排序; 对于具有相同姓名长度的再根据字符顺序进行排序?
- 答:返回一个二元组,可通过元组或者列表接受,二元组的内容为(字符长度,字符)
name = ["gllu","steven","hallye","klom","srae","samm"]
name.sort(key = lambda tuple_len_str : (tuple_len_str,len(tuple_len_str)))
print(name)
['gllu', 'hallye', 'klom', 'samm', 'srae', 'steven']
条件表达式
- 语法: 条件成立表达式 if 条件 else 条件不成立表达式
- p49 例4-5
vip_sort = int(input())
price = int(input())
print(price*0.97 if vip_sort == 0 else price*0.88)
0
100
97.0
骑车t = 50s + x / 3m/s
步行t = x / 1.2m/s
x = float(input("请输入距离(单位m)"))
t1 = 50 + x/3
t2 = x/1.2
if(t1 == t2):
print("一样快")
else:
print("骑车快" if t1<t2 else "步行快")
请输入距离(单位m)100
一样快
字典的key值可以是布尔类型吗
- 猜测:可以,因为布尔类型属于数值类型
dict_1 = {True:"123",False:"456",True:"789",True:"101112"}
print(dict_1[True])
dict_2 = {1:"1234",1:"5678",0:111,0:222}
print(dict_2[1])
101112
5678
数据容器.集合
集合的特性
唯一(不重复)、无序、不变(非数学)
- 唯一性:集合中的元素不能重复
- 无序性:相同元素构成的多个集合中若元素位置不同则都是同一个集合
- 字典也具有无序性
- 意味着元素没有位置⇒没有indx⇒不支持与位置相关的操作:索引、切片等
- 不变性:集合中的元素(对象)必须是不可变类型(数值、字符串、tuple)
例:关于无序性的一种体现,本例中即使传入了有序的列表但依旧生成了无序的集合
set_1 = {i**2 for i in range(1,13) if i%2==0}
sortlist_1 = sorted(set_1)
print(sortlist_1)
sortset_1 = set(sortlist_1)
print(sortset_1)
[4, 16, 36, 64, 100, 144]
{64, 100, 4, 36, 16, 144}
集合的类型
- 可修改型set
- 不可修改型集合frozenset
- set——可变类型集合(支持增删改)
- 集合的创建
- 创建非空集合:set_1 = {元素}
- 创建空集合:set_1 = set( )
- set(序列) 返回由序列生成的相应元素的集合
- 注:{ }只能创建非空集合,创建空集合只能通过set()函数实现
- 集合的创建
set_1 = set()
print(f"set_1 class is : {type(set_1)}")
set_2 = {}
print(f"set_2 class is : {type(set_2)}")
set_1 class is : <class 'set'>
set_2 class is : <class 'dict'>
- frozenset 不可变类型(增删改)
- 可作为其他集合的元素(集合也可以嵌套)
集合推导式
集合 = {表达式 for 遍历可迭代对象获得的临时变量 in 迭代对象 if 条件语句}
- 含义:可迭代对象中的变量依次取出 并且 仅当条件语句为True时 才 求解表达式 将求解结果放入集合
- 例:求1~5中被2整除的数值的平方:
set_1 = {i**2 for i in range(1,6) if i%2==0}
print(set_1)
{16, 4}
增长集合
- 目标集合.add(添加的数据):添加一个数据
- 目标集合.update(可迭代对象):将可迭代对象中目标集合没有的元素添加进去
- 注:由于集合的不可变性——集合的对象都是不可变元素,所以增长集合的方法给出的集合的元素都要是不可变类型
缩减集合
- remove(元素)
- discard(元素)
- 注:二者的不同在于:
- 当集合中元素不在集合中时,remove会报错
- discard不论所删除的元素是否在集合中都会返回None,只不过当元素在集合中会删除,当元素不在集合中无法删除
- .pop() 删除任意一个元素
- 由于集合是无序的因此你无法预测/指定删除哪一个
- pop()可以用于遍历一个集合的所有元素
- .clear() :清空集合
#1.使用remove删除的元素不在集合中:
set_1 = {1,2,3}
set_1.remove(1024)
print(set_1)
---------------------------------------------------------------------------
KeyError Traceback (most recent call last)
Input In [25], in <cell line: 4>()
1 #1.使用remove删除的元素不在集合中:
2 set_1 = {1,2,3}
----> 4 set_1.remove(1024)
5 print(set_1)
KeyError: 1024
#2.使用discard删除的元素不在集合中:
set_1 = {1,2,3}
set_1.discard(1024)
print(set_1)
return_val = set_1.discard(1)
print(return_val) #不论是否成功删除,discard都是返回None
print(set_1)
{1, 2, 3}
None
{2, 3}
访问集合中的元素
- in 判断元素是否在集合中
- .pop() 删除元素并返回其的值
- 迭代循环:for a in set_1
集合的运算
-
运算后生成新集合
|运算|运算符|新集合方法|更新原集合方法|
|—|—|—|—|
|并| a|b |union|update|
|交| a&b |intersection|intersection_update|
|差| a-b |difference | difference_update|
|对称差(将公共元素去掉)|a^b|symmetric_difference|symmetric_difference_update| -
集合关系的判定
- 两集合交集是否为空判定:
- 语法:集合1.isdisjoint(集合2)
- 若两集合存在交集⇒返回True,若没有交集⇒返回Flase
- 两集合关系判定:
集合关系 运算符 例 子集 <= set1 <= set2#set1是set2的子集吗 真子集 < set1 < set2#set1是set2的真子集吗 相等 == set1 == set2#set1和set2是否相等 超集 >= set1 >= set2#set1是set2的超集吗 真超集 > set1 > set2#set1是set2的真超集吗
集合的应用
- 快速的去重复的数据项
- 判断一个元素是否在数据集中,如果这些数据的次序不重要,使用集合能够获得比列表更好的性能
集合的应用
- 快速的去重复的数据项
- 判断一个元素是否在数据集中,如果这些数据的次序不重要,使用集合能够获得比列表更好的性能