Python3学习(5)--集合dict和set

     接着上一篇,今天仍然讲Python的集合,上一篇,我们认识了列表list和元组tuple,对比今天将的dict和set,你会发现,之所以分开成对来讲,是因为,list和tuple中的元素是可以重复出现的,而dict和set中的"元素"是不会出现重复的,就算你给它们初始化的时候故意放几个重复的值,但是正式使用它们的时候,dict和set会自动过滤掉这些重复的"元素",这里的元素之所以打引号,是区别于list和tuple中的元素,下面细讲的时候再说明,上几张图,先来个直观体现:

 

 

lis-->[一对中括号,有序,可变]t:

 

 


tuple-->[一对括号,有序,不可变]:

 


 

dict-->[一对花括号,键值对的存储结构,类似字典,无序,key唯一(不可变),value值只有一个,一一对应,存放不可变对象]:

 

 


 

set-->[一对花括号,key存储,无序,key唯一,key必须是不可变对象]:

 

 

 

 

一、dict

 

Python内置了字典:dict的支持,dict全称dictionary,在其他语言比如java中也称为map,使用键-值(key-value)存储,具有极快的查找效率。

a结构:D = {key:value1,key2:value2......} 类似于JSON(轻量级的数据交换格式),注意,dict中,字符串存在的最终方式是以单引号的形式

 


b.长度:len(D)  --> 表示dict中包含了几对  键值结构,也就是有几个key值


c.空字典:D = {}  len(D) = 0

 

(1)dict的查找效率

 

我们都用过字典,我们知道查找一个汉字,有两种方式:

A、手动翻找,从第一页翻到这个字出现的那一页,如果字很多的话,我们需要做大量的翻找工作,这就好比list中存放了大量的汉字,你要找到你需要的,你需要从第0个元素一直往后找,查找效率和list的容量成反比,list越长,查找效率越慢

B、根据字典提供的索引查找(比如笔画),这样只要知道我们要查找的字的笔画有多少,我们就可以通过页码数(索引页)快读定位,从而节省了我们逐一翻找的时间,而且这种查找效率不会随着dict的长度增加而变慢。

 


 

(2)dict的键值对   ------  key-->value

 

由于字典不可能出现,同一个字,在第100页可以找到,而在256页也可以查到,如果出现这种情况,你会怀疑是自己看错了,还是怀疑字典出版的有问题?

 


因此,dict中的key是唯一的,value值也就必然只有一个,也就是说,value的唯一性是由key值决定的,试想一下,如果初始化dict的时候,我们让key值有好几个的同时,同时让其对应的value值不同,模拟下一个字对应好几个页码,下面看下效果输出:

 

 


由于dict会过滤掉重复的key值,这就好比,字典里面只能出现一个汉字'中'和'国',那么,dict会过滤掉哪个呢,是对应256页的,还是对应100页的?从图中我们可以看出来,dict去除重复键值对的机制是,只保留最后一对键值(因为dict是无序的,所以只有先后顺序可言),也就理所当然的,'中'对应的100页会保存下来,太少了看不出效果,我们继续来验证一下:

 

虽然这很无聊,我们实际初始化的时候不会这样做,但是,学习吗,就是要研究的透透的才有意思,哈哈。

 


 

插播一条注意事项:如果我们访问的key不存在会不会有结果输出呢,当然有,还必须是错误的提示'找不到key':

 

 


 

那怎么避免这种错误发生呢,这就需要我们访问拿不准的key的时候,判断一下dict里面是否含有这个key,我们可以这样做

 

 


 

我们也可以这么做

 

 


 

上面我们可以看出,key值是固定的,但是value值是变化的,比如,字典里面,如果我们增加了一个字,增加的这个字会有什么影响呢?首先,字典字变多了,其次每个字对应的页码数不能保证和之前一样了,但是,我们可以肯定的是,除了这个新增的字以外的其他字没变,还是那么个写法那么个笔画(你大爷还是你大爷啊),比如在"中"字前增加了一个字,这个字假设占了一页(信息量太大,不是没可能,哈哈),这个时候,我们重新修订字典,此时我们发现'中'字跑到了101页,如下:

 

 


因此,我们得出结论,对于dict来说,key是不可变的,但是value是可以修改的。

前面我们讲过,集合里面可以包含集合,dict也不列外,这里key我们可以用list和tuple对象来代替,那么问题来了,都可以吗?

试一下list:

 

 


 

我们再试一下tuple,实现这样一个功能,我们列举出现役的NBA球星

 

 


 

如果按照正常的dict初始化的话,虽然我们知道这三个人都是现役球员,但是我们需要初始化三遍,我们取出具有相同value值的key,将key编进一个tuple元组里,我们这样来修改一下:

 

 

因为tuple是不可变的,因此可以作为key!

 


 

(3)dict的插入和删除

 

1,插入(增加键值对)

 

由于dict是无序的,所以插入元素的话,没有什么讲究,直接创建一对键值就行,非常效率

 

 


 

2,删除(pop(key))

由于dict是无序的,不能用pop()默认弹出最后一个,必须指定要删除的键值对的 key是多少,key有可能是一个值,也有可能是一个对象,我们这里删除的key是一个 tuple对象,接着上图来

 

 


 

(4)dict的特点

1. 查找和插入的速度极快,不会随着key的增加而增加;
2. 需要占用大量的内存(key和value是两块区域),内存浪费多

 

 

二、set

 

set和dict类似,也是一组key的集合,但不存储value;也是无序存储;由于key不能重复,所以,在set中,也是没有重复的key。

结构:  {key1,key2,key3....}

创建方式:S=set(list),list的元素将作为set的元素

 

空集合:S=set([])   --> set()  -->    len(S) = 0

 



(一)set的key访问?

 

由于set是无序存储,所以,无法通过索引访问元素

 

 


 

由于set只有key,没有value,所以这样写是没有任何意义的S['a']

 

 


 

事实上,我们访问set的某个key,其实就是判断这个key是否存在,我们同样用in属性来判断

 


我们虽然不能直接访问key,但是我们可以遍历set来获取所有的key

 


 

 

(二)添加key

 

直接add(),因为无序,你不用管添加到哪个位置,set会为你考虑,如果添加的key已经存在了,你的添加行为会被无视。

 

 


 

插播一条注意事项:插入的key,同样可以是一个对象,由于我们知道,key值是唯一的,所以key值如果指向一个对象,那么,这个对象(集合)也必须是不可变的,这样的话才能保证我们的key仍然满足唯一的特性,例如,我们前面讲的list和tuple,前者是可变的,元素可以被修改,后者是不变的,元素一旦初始化赋值是不能被修改的,针对set的key特性,我们来分别为S添加一个list和一个tiple,对比下效果(dict同理)

S.add(list):

 

 


 

添加list报错

S.add(tuple):

 

 


 

添加tuple,ok,完全没问题

再来看一个可变和不可变集合的差异所在:

 

 


 

(三)删除key

 

remove(key)

 

 

如果key存在,删除成功,如果key不存在,会提示删除的key错误,这时,可以先判断一下key是否存在,再行删除

 


 

(四)数学意义上的交集(&)和并集(|)

 

 


 

(五)清空set-->clear()

 

 


 

 

小结:dict是一个非常有用的存在,且key大多数情况下使用字符串,key和value一一对应,且key指向的对象是不可变的。

            set和dict类似,只不过少了value的存储,且key也是唯一存在,无重复值,指向的对象也必须是不可变的。

注:凡是key出现了  [..]的身影,一律是不行的,比如,tuple虽然是不可变的,如果这样添加到set(dict也一样)中,是会报错的:

 

 

 


 

结束语:写代码的乐趣不在于实现了某个功能,而在于写的过程中不断地探索和深入,这才是最有意思的。

 

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值