【Python练习cookbook】字典dictionary高级操作

1.字典键-值对中,值元素的便捷创建增减

主要是利用collections 中的defaultdict

普通复杂过程:

pairs = [('a', 1), ('a', 2),('b', 2)]
d = {}
for key, value in pairs:
    if key not in d:
        d[key] = [] #指定值为list类型
    d[key].append(value)

d = {} #普通字典
d.setdefault('a', []).append(1)
d.setdefault('a', []).append(2)
d.setdefault('b', []).append(4)

当我们使用普通的字典时,还可以dict={},添加元素的只需要dict[element] =value,调用的时候也是如此,dict[element] ,但前提是element在字典里,如果不在字典里调用就会报错

利用defaultdict就没这些问题,且精简:

defaultdict接受一个工厂函数作为参数,如下来构造:

dict =defaultdict( factory_function)

这个factory_function可以是list、set、str等,有两个作用,第一是当调用的key不存在时,返回的是工厂函数的默认值,比如list对应[ ],str对应的是空字符串,set对应set( ),int对应0,第二是可以对值做操作是调用相应类的函数

from collections import defaultdict

d = defaultdict(list)
for key, value in pairs:
    d[key].append(value)

d = defaultdict(list)
d['a'].append(1)
d['a'].append(2)
d['b'].append(4)

d = defaultdict(set)
d['a'].add(1)
d['a'].add(2)
d['b'].add(4)

2.创建带顺序的字典

from collections import OrderedDict

d = OrderedDict()
d['foo'] = 1
d['bar'] = 2
d['spam'] = 3
d['grok'] = 4
# 输出 "foo 1", "bar 2", "spam 3", "grok 4"
for key in d:
    print(key, d[key])

若后续修改已插入的键值,不改变字典的顺序。顺序字典的内存开销是比较大的,若数据量很大(比如100,000条以上),则考虑使用其他结构保存数据。

 顺序字典的一个应用实例,json串构造:

>>> import json
>>> json.dumps(d)
'{"foo": 1, "bar": 2, "spam": 3, "grok": 4}'

 

3.字典排序相关

prices = {
    'ACME': 45.23,
    'AAPL': 612.78,
    'IBM': 205.55,
    'HPQ': 37.20,
    'FB': 10.75
}
# 通常:
min(prices)  # Returns 'AAPL'
max(prices)  # Returns 'IBM'
min(prices.values())  # Returns 10.75
max(prices.values())  # Returns 612.78

# 高级一点:
min(prices, key=lambda k: prices[k])  # Returns 'FB'
max(prices, key=lambda k: prices[k])  # Returns 'AAPL'
min_value = prices[min(prices, key=lambda k: prices[k])]
sorted(prices, key=lambda k: prices[k])# Returns ['FB', 'HPQ', 'ACME', 'IBM', 'AAPL']

# 以上都要想获取较全的键值信息都比较繁琐,可转化成(值,键)进行排序
min_price = min(zip(prices.values(), prices.keys()))
# min_price is (10.75, 'FB')
max_price = max(zip(prices.values(), prices.keys()))
# max_price is (612.78, 'AAPL')
prices_sorted = sorted(zip(prices.values(), prices.keys()))
# prices_sorted is [(10.75, 'FB'), (37.2, 'HPQ'),
# (45.23, 'ACME'), (205.55, 'IBM'),
# (612.78, 'AAPL')]

注意zip生成一个迭代器,只能用一次

另外:也可将字典转为list:li=list(prices.items()),用【Python练习册】heapq的应用 的方法来排序

 

4.两个字典间找异同--三种构造方式对比

dict.keys()和dict.items分别为dict_keys和dict_items对象,具体叫做keys-view和items-view对象,之所以叫view是因为,随着dict的变化,这些view也自动改变。keys-view和items-view对象支持常规set操作,如求交集、并集、差集等。

a = {
    'x': 1,
    'y': 2,
    'z': 3
}
b = {
    'w': 10,
    'x': 11,
    'y': 2
}
# 找相同键
a.keys() & b.keys()  # { 'x', 'y' }
# 找在a中不在b中的键
a.keys() - b.keys()  # { 'z' }
# 找相同元素
a.items() & b.items()  # { ('y', 2) }

# 移除特定键构建新字典
c = {key: a[key] for key in a.keys() - {'z', 'w'}}
# c is {'x': 1, 'y': 2}

#也可如下构造--最快,没有a[]的查询过程
p2 = { key:value for key,value in a.items() if key not in {'z', 'w'}}

#也可如下构造--最慢
p1 = dict((key, value) for key, value in a.items() if key not in {'z', 'w'})

注意:dict.values是values-view对象,但不支持常规set操作,因为value值可以不唯一

 

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值