小甲鱼零基础学习python_14 【深吸一口老气!老多内容的字典入门知识】

字典

每次学习一个新的数据类型,都需要写一堆,从创建,修改,删除,访问以及相关基础函数来介绍,比如元组,列表,字符串等…..今天要记录的是字典,其实字典并不是一个数据类型,而是一个映射类型,类似于数据结构,操作系统提到的hash,是一个类似索引的东东。

今天就从:创建,修改,删除,访问基础函数四个大块来基本介绍字典叭~

一. 创建一个字典:

字典 python唯一一个映射类型, 类似于hash;是两个元素集之间对应的关系
字典的两大重要部分: 键key – 值value

A.创造一个空的字典

dictnull={}
#花括号是字典的典型符号,就类似于:逗号是元组的典型;[]是列表的典型....

B.创建一个有键值的字典

1. 大括号表示字典–映射类型; 前面是键,后面是值 冒号隔开
dict1= {'李宁':'一切皆有可能', '耐克':'just do it'}
print('李宁的口号:', dict1['李宁'])


dict2={1:'one', 2:'two'}
print('1的英文: ', dict2[1])

这里写图片描述

dict严格来说不是bif,而是一个工厂函数(类型)
2.1 dict()关键字 入口参数只能有一个 所以得打包输入多个字,可以用元组,列表…..
dict3=dict((('A',70),('B',80),('C',67)))  #(('A',70),('B',80),('C',67))是一个元组
print(dict3)
2.2 用关键字创建字典 前面是键,后面是值 创建的时候键不用单引号,自动会被转化为字符串
dict4=dict(yhr='1',aka='2')
print(dict4)

这里写图片描述

3. fromkeys(s,[v]) 创建并返回一个新的字典 s–键 v–值,值默认为none
(fromkeys仅仅是创建新的字典,并没有改变dict本身!)
a. 值默认为none时:
dict5={}
dict5.fromkeys((1,2,3))   #仅仅是创建新的,并没有改变dict5本身
print(dict5)

dict5=dict5.fromkeys((1,2,3)) #赋值后才算改变dict5本身
print(dict5)

这里写图片描述

b. 值为一个参数时:值会给每个键赋值
dict5=dict5.fromkeys((1,2,3), 0)
print(dict5)

这里写图片描述

c. 值为多个参数时:全部值会分配给每个键,而并不是值每个对应分配一个
dict5=dict5.fromkeys((1,2,3),('哈哈哈','赞赞赞','咳咳咳')) 
  #全部值会分配给每个键,而并不是值每个对应分配一个
print(dict5)

这里写图片描述

d. 不能用fromkeys批量修改字典 因为fromkeys是重新创建一个字典
dict5=dict5.fromkeys((1,3),'数字')
print(dict5)

这里写图片描述


二. 修改一个字典:

A. 直接给字典键赋值,如果键存在,则改变值,若不存在,则自动创建并赋值;
字典跟序列不一样,序列若为不存在的值赋值则会报错
#先创建一个字典
dict4=dict(yhr='1',aka='2')
print(dict4)

#修改一个字典,直接给字典键赋值
dict4['foyn']='3'
dict4['yhr']='0'
print(dict4)

这里写图片描述

B. update()方法:利用一个字典或者映射关系 去更新另外一个字典
#先创建一个字典
dict5=dict(yhr='1',aka='2')
print(dict5)

#修改一个字典,利用一个字典或者映射关系 去更新另外一个字典 
b = {'小白':'dog','yhr':'3'}
dict5.update(b)
print(dict5)

这里写图片描述

可以看出,update方法的入口参数是一个字典;效果仅仅是在源字典上修改新增,不会全盘覆盖。


三. 删除一个字典:

A.使用={} 方法,不能级联删除
dict5=dict5.fromkeys((1,2,3),'numbers')
print(dict5)

#将dict5赋值给dict6
dict6=dict5
print('dict5',dict5)
print('dict6',dict6)

#使用={} 方法,不能级联删除
dict5={}
print('dict5={}',dict5)
print('dict6',dict6)

这里写图片描述

B. 使用clear 方法,能级联删除 —- √ clear()更为安全

dict5=dict5.fromkeys((1,2,3),'numbers')
print(dict5)

#将dict5赋值给dict6
dict6=dict5
print('dict5',dict5)
print('dict6',dict6)

#使用clear 方法,能级联删除
dict5.clear()
print('dict5.clear()',dict5)
print('dict6',dict6)

这里写图片描述

C. pop() 给定键 弹出对应值; popitem() 弹出项
dict5=dict5.fromkeys((1,2,3,4,5,6,7),'numbers')
print(dict5)
dict5.pop(2)
print(dict5)

#没有顺序,随机弹出
dict5.popitem()
print(dict5)

这里写图片描述


四. 访问一个字典:

A. 使用键查找方法 – print(dict5[6])

dict5=dict5.fromkeys((1,2,3),'fangwen')
print(dict5)

#访问项,根据键 返回值
print(dict5[1])

这里写图片描述

访问不存在的项,报错:

#访问不存在的项,报错
print(dict5[0])
File "D:/pyTest/zidian.py", line 83, in <module> 
print(dict5[0])
KeyError: 0

B. get()更宽松的访问方法,如果试图访问不存在的item,则返回none,还可以使用不存在的时候自定义提示值

dict5=dict5.fromkeys((1,2,3),'fangwen')
print(dict5)

print(dict5.get(6))

#也可以设置找不到的情况处理
print(dict5.get(6,'木有'))

这里写图片描述

C. setdefault() 类似于get() 但是找不到对应的值得时候会进行添加

dict5=dict(yhr='1',aka='2')
print(dict5)

dict5.setdefault('aka','seven')
print(dict5)

dict5.setdefault(7,'seven')
print(dict5)

这里写图片描述

D. 字典中也可以使用成员资格操作符 in not in : 字典中查找键 索引中查找值
dict5=dict5.fromkeys((1,2,3),'fangwen')
print(dict5)

print((6 in dict5))
print((6 not in dict5))

这里写图片描述

E. 其他访问字典的几个方法 keys() values() items()
dict5=dict5.fromkeys(range(5),'赞')
print(dict5)
keys() 返回字典键的引用
for eachKey in dict5.keys():
    print(eachKey)
values()返回每个值
for eachValue in dict5.values():
    print(eachValue)
items()返回每个项
for eachItem in dict5.items():
    print(eachItem)

这里写图片描述


五. 浅拷贝 copy() 的引入:

浅拷贝copy()–仅仅拷贝对象,不拷贝地址;

赋值不是浅拷贝,类似于贴标签,实际上地址不变。

a={1:'one',2:'two'}

b=a.copy()  #浅拷贝copy()
c=a   #赋值

print(a)
print(b)
print(c)

这里写图片描述

对象看起来,abc完全一样,那下面我们从地址来区分copy()方法和 赋值的区别:

print('a:', id(a))
print('b:', id(b))
print('c:', id(c))

这里写图片描述

可以看出,经过浅拷贝的b地址,与原先的a,指向不同的地址;然而c与a却指向相同的地址;
尝试修改c,监视abc的变化:

c[4]='four'
print(a)
print(b)
print(c)

这里写图片描述

可以看出b不受c影响,但是a与c同步变化,再次印证了:

浅拷贝copy()–仅仅拷贝对象,不拷贝地址;

赋值不是浅拷贝,类似于贴标签,实际上地址不变。


六. 我的疑问:

但是我认为奇怪的是!!!!

c={}
print(a)
print(b)
print(c)

这里写图片描述
c单纯置空时,a却不随c变化了!

但是用clear()方法则级联删除:


c.clear()
print(a)
print(b)
print(c)

这里写图片描述

确实上文提过简单的置空和clear方法,在简单的赋值情况下,一个可级联删除,一个不可;但是如果ac真的是指向同一个地址,用c-like语言的知识,修改的c,岂不是a不管怎么也会修改的,为何这里c={}操作后,a不变呢?
希望看到这里的小伙伴有想法的话能和我一起探讨一下,希望这个疑惑终会被解答….

不出一会儿就有热心的WUZA同学为我指点迷津了:
当c={}时,c执行了赋值操作,相当于指针指向了别的地址,c与a关系分开:

c={}
print(a)
print(b)
print(c)

print('a:', id(a))
print('b:', id(b))
print('c:', id(c))

这里写图片描述

但是执行clear操作时,仅仅是使用了内置函数,并没有改变c的地址,c与a仍然指向同一个地址,所以改变是同步的!


  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值