深浅拷贝
浅拷贝的原理
拷贝后,无论是可变类型还是不可变类型都公用一个id,共用一个内存地址
案例:
l = [11, 22, ["aa", "bb"]]
l2 = l[:]
l[2][0] = 55
print(l2) # [11, 22, [55, 'bb']]
print(l) # [11, 22, [55, 'bb']]
print(id(l), id(2))
l2 copy l,当l2中的子列表值改变后,l中的子列表值也会发生变化,查看l,l2的id是一样的
深拷贝的原理
拷贝后,可变类型的子列表id发生了变化,不共用一个内存地址
案例:
l = [11, 22, ["aa", "bb"]]
from copy import deepcopy
l1 = deepcopy(l) # id会发生变化,子列表不在一个内存空间
l1[2][1] = "zz"
print(l) # [11, 22, ['aa', 'bb']]
print(l1) # [11, 22, ['aa', 'zz']]
print(id(l), id(l1))
l1copy l,当l1的子列表值发生改变后,l的子列表值不会发生改变,查看l, l1的id是不一样的
总结:
深度copy与浅度copy的差别在于,浅度copy的子列表跟原列表的子列表共用一个id,改变共用一个子类表中的值后,那么原列表的值也会发生变化。
深度copy的子类表开辟了新的内存空间,所以无论是改变原列表中子列表的值还是改变copy后的子列表中的值,两者都不会有相关联。我们改列表类型其实就是在索引于内存地址的对应关系。
列表
需要掌握的方法调用:
.copy,len,.index,.count,.clear,.extend,.append,.reverse,.sort
l = [11, 22, 33, 44, 55, 33, 33]
l1 = l.copy() #等同于l1=l[:]
print(l1) #[11, 22, 33, 44, 55]
print(len(l)) #显示列表中l值的个数7
print(l.index(11))#显示列表中出现的某一个值的索引(11的索引为0),如果值中没有这个元素,那么会报错
print(l.count(33))#统计一个列表中同一个索引出现的个数,33出现了3次
print(l.clear()) #清空列表,为none
l.extend("hello")
.extend只能往列表里面加可迭代的值,比如列表,字符串等
print(l) #往列表里面加值[11, 22, 33, 44, 55, 33, 33, 'h', 'e', 'l', 'l', 'o']
l.extend([1,2,3])
print(l) #往列表里面加值[11, 22, 33, 44, 55, 33, 33, 1, 2, 3]
l.append([1,2,3])
print(l) #往列表里面加了一个列表[11, 22, 33, 44, 55, 33, 33, [1, 2, 3]]
l.reverse()
print(l) #把列表里面的值都反过来[33, 33, 55, 44, 33, 22, 11]
l.sort()
print(l) #把列表里面的值按照从小到大排序[11, 22, 33, 33, 33, 44, 55]
l.sort(reverse=True) #把列表里面的值按照大到小排序[55, 44, 33, 33, 33, 22, 11]
print(l)
总结:
列表可以存多个值
有序
可变类型的值
元组
工厂元素:tuple
用途:元组相当于不可变的列表,可以存放多个任意类型的值,定义好值后就不能再做更改。
数据只能读不能改的时候可以选用元组
定义方式:在()用逗号分隔开多个任意的元素
数据类型转换:tuple(可迭代的类型)
注意:如果元组内只有一个元素,必须用逗号分隔
a=(11,)
print(type(a))类型为tuple
常用操作+内置方法
优先掌握的操作
1.按索引取值(正向取+方向取):只能取
a = (11, 22, 33)
a[0] = 7777
print(a) # 会报错,元组的值不能做更改
2.切片(顾头不顾尾,步长)
a=(11,22,3,4,5,6,66,777)
print(a[0:5:2]) # 取值结果为(11, 3, 5)
3.长度
a=(11,22,3,4,5,6,66,777)
print(len(a)) # 取值结果为8
4.成员运算
a=(11,22,[ 44,55,66],7)
print([ 44,55,66]in a) # 取值结果为True
5.循环
a=(11,22,[ 44,55,66],7)
for x in a:
print(x)
取值结果
为11 22 [44, 55, 66] 7
总结:
存多个值
有序
子元素不可变
t=(11,22,[11,22])
t[1]=33
print(t[1]) # 报错,不能改
t[2][0]=333333
print(t) # (11, 22, [333333, 22])
元组里面的列表值可以改,改完列表元组里面的元素id不会发生改变
字典类型
工厂函数 dict
用途:按照key:value的方式存放多个值,其中key对value应该有描述性效果
定义方式:适用于存放多个不同类型的值,在{}内用逗号分隔开多个元素,每个元素都是key:value的组合,其中value
可以时任意类,但是key通常都时字符串类型,必须是不可变类型。在字典中,key不能重复,但是value可以重复。
d = {
1: 1111, 1.1: 2222222, "k1": 66666, (1, 2, 3): 44444}
print(d[1]) # 1111
print(d[1.1]) # 2222222
print(d["k1"]) # 66666
print(d[(1, 2, 3)]) # 44444
如果在d中加入列表类型那么不会保存,字典类型只能存放不可变类型的值
数据类型转换
dict的数据类型转换比较狭窄,必须是key,value的形式
res = dict(["name", "age", "gender"]) #报错
res=dict([("name","egon"),["age",18]])
print(res) #{
'name': 'egon', 'age': 18}
res=dict(a=1,b=2,c=3)
print(res) #{
'a': 1, 'b': 2, 'c': 3}
d={
} # 这是造空字典,默认d=dict{
}
print(type(d)) #<class 'dict'>
res={
}.fromkeys(["name","age","gender"],None)
print(res) #{
'name': None, 'age': None, 'gender': None}
res={
}.fromkeys(["name","age","gender"],[])
res["name"]=666
print(res) #{
'name': 666, 'age': [], 'gender': []}
res={
}.fromkeys(["name","age","gender"],[])
res["name"].append(111) #{
'name': [111], 'age': [111], 'gender': [111]}
print(res)
常用操作+内置方法
优先掌握的操作
1.按key在取值,可存可取
d={
"k1":111,"k2":222}
print(d["k1"]) #取值结果为111
d["k1"]=666
print(d) #{
'k1': 666, 'k2': 222} id 不变,字典是可变类型
d["k3"]=666
print(d) #{
'k1': 666, 'k2': 222, 'k3': 666}字典是可以天添加不存在的值的
2.长度len
d={
"k1":111,"k2":222,"k3":333}
print(len(d)) #字典长度统计的是key的个数,为3
3.成员运算in和not in
d={
"name":"nana","age":18}
print("nana"in d) #False
print("name"in d) #True
成员运算时判断的是key
4.删除
del, .pop, popitem
d={
"name":"nana","age":18}
del d["name"]
print(d) #{
'age': 18}
v=d.pop("name")
print(d) #{
'age': 18}
print(v) #nana 会返回删除的value的值
item=d.popitem()
print(item) #删除后会以元组的形势反馈出来('age', 18)
print(d) #随机删除,删除后的值{
'name': 'nana'}
5.键keys(),值values(),键值对items()
d={
"name":"nana","age":18}
print(d.keys()) #dict_keys(['name', 'age'])
print(d.values()) #dict_values(['nana', 18])
print(d.items()) #dict_items([('name', 'nana'), ('age', 18)])
6.keys,values在for循环里面的使用:
可以用来取key值,或者values值
d={
"name":"nana","age":18}
for k in d.keys():
print(k) #name age
for k in d:
print(k) #name age
for k in d.values():
print(k) #nana 18
7.d.get()
d={
"name":"nana","age":18}
print(d["name"]) # 取值结果为nana
print(d.get("name")) # 取值结果为nana
当字典里面不存在我们要取的值时:
print(d["xx"]) # 会报错keyerror:"xx"
print(d.get("xx")) # 报错信息为none
封装了if判断的取值功能
8.把字典型转换成列表型
print(list(d.keys())) # ['name', 'age']
print(list(d.values())) # ['nana', 18]
print(list(d.items())) # [('name', 'nana'), ('age', 18)]
需要掌握的内容
d={
"name":"nana","age":18}
d.clear()
print(d) # {
}
d.copy() # 浅copy # 复制d = {
"name":"nana","age":18}
d.update() # 深copy
d.update({
"k1":111,"name":"lala"})
print(d) #{
'name': 'lala', 'age': 18, 'k1': 111}
更新,如果原来字典里面有的值会直接覆盖,如果原来字典里面没有的值会添加到原字典
d.setdefault() # 深copy
key不存在则添加value,key如果存在则什么都不做
用if判断表示:
d={
"name":"nana","age":18}
if "gender" not in d:
d["gender"]="girl"
print(d) # {
'name': 'nana', 'age': 18, 'gender': 'girl'}
用d.setdefault()来表示:
d.setdefault("gender","girl")
print(d)
表示结果为:{
'name': 'nana', 'age': 18, 'gender': 'girl'}
a.setdefault("gender","xxx")
a = {
"name": "nana", "dada": "sg", "age": 18} # {
'name': 'nana', 'dada': 'sg', 'age': 18, 'gender': 'xxx'}
a = {
"name": "nana", "dada": "sg", "age": 18, "gender": "male"}
表示结果为:{
"name": "nana", "dada": "sg", "age": 18, "gender": "male"}
值如果存在那么就不管,值如果不存在往列表里面加值
总结
存一个值
无序
可变类型
案例:
d = {
"k1":111}
print(id(d)) # 6113352
d["k1"] = 222
print(id(d)) # 6113352
值改变,id不变