python字典(dict)
1、字典dict定义 初始化
key-value键值对的数据的集合,可变、无序、key不重复(哈希、唯一)
1> d = dict() 或者 d = {}
# -*- coding:utf-8 -*- # version:python3.7 d1 = dict() d2 = {} print(d1) print(d2) 执行结果: {} {}
2> dict(**kwargs)使用name=value对初始化一个字典
d1 = dict(a=1,b=2,c=3) #或着:d1 = {'a':1,'b':2,'c':3} print(d1) 执行结果: {'a': 1, 'b': 2, 'c': 3}
3> dict(iterable, **kwarg)使用可迭代对象和name=value对构造字典,不过可迭代对象的元素必须是一个二元结构
d = dict((('a',1),('b',2),('c',3))) #或者:d = dict([('a',1),('b',2),('c',3)]) print(d) 执行结果: {'a': 1, 'b': 2, 'c': 3}
4>dict(mapping, **kwarg)使用一个字典构建另一个字典
l1 = [3,4] d1 = dict(a=1,b=2,c=l1) d2 = dict(d1) print(d1) print(d2) print(d2 == d1) print(d2 is d1) l1.append(5)
print(d1)
print(d2)
执行结果: {'a': 1, 'b': 2, 'c': [3, 4]} {'a': 1, 'b': 2, 'c': [3, 4]} True False
{'a': 1, 'b': 2, 'c': [3, 4, 5]}
{'a': 1, 'b': 2, 'c': [3, 4, 5]}
5>类方法dict.fromkeys(iterable, value=None)
d1 = dict.fromkeys(range(5)) d2 = dict.fromkeys(range(5),0) print(d1) print(d2) 执行结果: {0: None, 1: None, 2: None, 3: None, 4: None} {0: 0, 1: 0, 2: 0, 3: 0, 4: 0}
6>key可哈希、不重复、可去重
d = {'a':1,'a':2} print(d) 执行结果: {'a': 2}
2、字典元素的访问
d[key]
返回key对应的值value
key不存在抛出KeyError异常
get(key[, default])
返回key对应的值value
key不存在返回缺省值,如果没有设置缺省值就返回None
setdefault(key[, default])
返回key对应的值value
key不存在,添加kv对,value设置为default,并返回default,如果default没有设置,缺省为None
# -*- coding:utf-8 -*- # version:python3.7 d1 = dict(a=1,b=2,c=3,d=4) print(d1) print(d1['a']) # 不存在则抛出 KeyError 异常 print(d1.get('b')) print(d1.get('e')) # 不存在返回None print(d1.setdefault('d','e')) # 返回key对应的value值 print(d1.setdefault('e',5)) # key值不存在,创建kv对 print(d1) 执行结果: {'a': 1, 'b': 2, 'c': 3, 'd': 4} 1 2 None 4 5 {'a': 1, 'b': 2, 'c': 3, 'd': 4, 'e': 5}
3、字典的增加和修改
[key] = value
将key对应的值修改为value
key不存在添加新的kv对
update([other]) → None
使用另一个字典的kv对更新本字典
key不存在,就添加
key存在,覆盖已经存在的key对应的值
就地修改
# -*- coding:utf-8 -*- # version:python3.7 d1 = dict(a=1,b=2,c=3,d=4) print(d1) d1['d'] = 3 # 将key对应的值修改为value print(d1) d1['e'] = 4 # key不存在添加新的kv对 print(d1) d1.update({'b':3,'e':1}) print(d1) 执行结果: {'a': 1, 'b': 2, 'c': 3, 'd': 4} {'a': 1, 'b': 2, 'c': 3, 'd': 3} {'a': 1, 'b': 2, 'c': 3, 'd': 3, 'e': 4} {'a': 1, 'b': 3, 'c': 3, 'd': 3, 'e': 1}
4、字典删除
pop(key[, default])
key存在,移除它,并返回它的value
key不存在,返回给定的default
default未设置,key不存在则抛出KeyError异常
popitem()
移除并返回一个任意的键值对
字典为empty,抛出KeyError异常
clear()
清空字典
# -*- coding:utf-8 -*- # version:python3.7 d1 = dict(a=1,b=2,c=3,d=4) print(d1) d1.pop('d') print(d1) print(d1.pop('e',None)) # 不存在返回缺省值,可以判断key值是否存在 d1.popitem() # 随机弹出 print(d1) d1.clear() print(d1) 执行结果: {'a': 1, 'b': 2, 'c': 3, 'd': 4} {'a': 1, 'b': 2, 'c': 3} None {'a': 1, 'b': 2} {}
del语句
# -*- coding:utf-8 -*- # version:python3.7 a = True b = [2] d = {'a':1,'b':b,'c':[3,4]} print(d) del a # 引用计数归零 del b[0] # 删除成空列表 print(b) c = b # 引用计数加1 del d['c'] print(d) 执行结果: {'a': 1, 'b': [2], 'c': [3, 4]} [] {'a': 1, 'b': []}
看着像删除了一个对象,本质上减少了一个对象的引用,del实际上删除的是名称,而不是对象
5、字典遍历
for ... in dict
遍历key
for k in d:
print(k)
for k in d.keys():
print(k)
# -*- coding:utf-8 -*- # version:python3.7 d = dict((('a',1),('b',2),('c',3))) for k in d: print(k) print('*' * 10) for k in d.keys(): # 遍历key,建议使用d.keys() print(k) 执行结果: a b c ********** a b c
遍历value
for k in d:
print(d[k])
for k in d.keys():
print(d.get(k))
for v in d.values():
print(v)
# -*- coding:utf-8 -*- # version:python3.7 d = dict((('a',1),('b',2),('c',3))) for k in d: print(d[k]) print('*' * 10) for k in d.keys(): print(d.get(k)) print('*' * 10) for v in d.values(): print(v) 执行结果: 1 2 3 ********** 1 2 3 ********** 1 2 3
遍历item,即kv对
for item in d.items():
print(item)
for item in d.items():
print(item[0],item[1])
for k,v in d.items():
print(k,v)
for k,_ in d.items():
print(k)
for _,v in d.items():
print(v)
# -*- coding:utf-8 -*- # version:python3.7 d = dict((('a',1),('b',2),('c',3))) for item in d.items(): print(item) print('*' * 10) for item in d.items(): print(item[0],item[1]) print('*' * 10) for k,v in d.items(): print(k,v) 执行结果: ('a', 1) ('b', 2) ('c', 3) ********** a 1 b 2 c 3 ********** a 1 b 2 c 3
6、总结
Python3中,keys、values、 items方法返回一个类似一个生成器的可迭代对象,不会把函数的返回结果复制到内存中
返回Dictionary view对象,可以使用len()、iter()、in操作
字典的entry的动态的视图,字典变化,视图将反映出这些变化
keys返回一一个类set对象,也就是可以看做一个set集合
如果values都可以hash,那么items也可以看做是类set对象
Python2中,上面的方法会返回一 个新的列表,占据新的内存空间。所以Python2建议使用iterkeys、itervalues、iteritems版本, 返回一个迭代器,而不是返回一个copy
7、字典遍历和移除
如何在遍历的时候移除元素
错误做法:
d = dict(a=1,b=2,c=3,d=4,e=5) for k in d: d.pop(k) #RuntimeError异常
d = dict(a=1,b=2,c=3,d=4,e=5) while len(d): # 等同于 while d: print(d.popitem()) # 相当于清空字典,不如直接clear()
正确做法:
# -*- coding:utf-8 -*- # version:python3.7 keys = [] d = dict(a=1,b=2,c=3,d=4,e=5) print(d) for k,v in d.items(): if v > 4: keys.append(k) for k in keys: d.pop(k) print(d) 执行结果: {'a': 1, 'b': 2, 'c': 3, 'd': 4, 'e': 5} {'a': 1, 'b': 2, 'c': 3, 'd': 4}
8、字典的key
key的要求和set的元素要求一致
set的元素可以就是看做key,set可以看做dict的简化版
hashable可哈希才可以作为key,可以使用hash()测试
9、defaultdict 缺省字典
collections.defaultdict([default_factory[, ...]])
第一个参数是default_factory,缺省是None,它提供一 个初始化函数。当key不存在的时候,会调用这个工厂函数来生成key对应的value
构造一个字典,values是列表,为其添加随机个元素
# -*- coding:utf-8 -*- # version:python3.7 import random d = {} for k in 'abcde': for v in range(random.randint(1,5)): if k not in d.keys(): d[k] = list() d[k].append(v) print(d) 执行结果: {'a': [0, 1, 2], 'b': [0, 1, 2, 3, 4], 'c': [0, 1], 'd': [0, 1], 'e': [0, 1]}
# -*- coding:utf-8 -*- # version:python3.7 import random d = {} for k in 'abcde': for v in range(random.randint(1,5)): #d.get(k, []).append(v) #key不存在返回缺省值(该方法此处不合适!) d.setdefault(k, []).append(v) #key不存在,添加kv对,返回缺省值 print(d) 执行结果: {'a': [0, 1, 2, 3], 'b': [0, 1, 2], 'c': [0, 1, 2], 'd': [0, 1, 2, 3, 4], 'e': [0, 1, 2, 3]}
# -*- coding:utf-8 -*- # version:python3.7 from collections import defaultdict import random d = defaultdict(list) #函数名称 for k in 'abcde': for v in range(random.randint(1,5)): d[k].append(v) # d[k] = list() 函数名称后加(),函数调用 print(d) 执行结果: defaultdict(<class 'list'>, {'a': [0, 1, 2, 3, 4], 'b': [0, 1], 'c': [0, 1, 2, 3, 4], 'd': [0, 1, 2, 3, 4], 'e': [0]})
# -*- coding:utf-8 -*- # version:python3.7 from collections import defaultdict import random d = defaultdict(set) #函数名称 for k in 'abcde': for v in range(random.randint(1,5)): d[k].add(v) # d[k] = set() 函数名称后加(),函数调用 print(d) 执行结果: defaultdict(<class 'set'>, {'a': {0, 1, 2}, 'b': {0}, 'c': {0, 1, 2}, 'd': {0}, 'e': {0, 1, 2, 3}})
10、有序字典 OrderedDict
collections.OderedDict([items])
key并不是按照加入的顺序排列,可以使用OrderedDict记录顺序;
有序字典可以记录元素插入的顺序,打印的时候也是按照这个顺序输出打印;
3.6版本的Python的字典就是记录key插入的顺序(IPython不一定有效果);
建议:要想记录字典的插入顺序,请使用OrderedDict
# -*- coding:utf-8 -*- # version:python3.7 from collections import OrderedDict d = dict() d['a'] = 1 d['b'] = 2 d['c'] = 3 d['d'] = 4 print(d) 执行结果: {'a': 1, 'b': 2, 'c': 3, 'd': 4}
应用场景:
假如使用字典记录了N个产品,这些产品使用ID由小到大加入到字典中
除了使用字典检索的遍历,有时候需要取出D,但是希望是按照输入的顺序,因为输入顺序是有序的
否则还需要重新把遍历到的值排序