[笔记] Python核心编程 第七章
一个字典对象是可变的,它是一个容器类型,能存储任意个数的Python对象,其中也包括其他容器类型。
字典类型中的数据是无序排列的。
可以通过fromkeys()函数来创建一个“默认”字典
>>> dict_ = {}.fromkeys(('x', 'y'), -1)
>>> dict_
{'y': -1, 'x': -1}
>>> dict_ = {}.fromkeys(('foo', 'bar'))
>>> dict_
{'foo': None, 'bar': None}
用来检测字典中是否包含某个key,可以用has_key()方法,但这个方法已经逐渐被in或者not in操作符取代,所以不再推荐使用。
字典支持所有的标准操作符,除了连接(+)和重复(*)。
用cmp()内建函数比较字典的原则如下,按顺序比较:
1.比较字典长度
2.如果字典长度相同,那就按照字典的键比较;键比较的顺序和keys()方法返回键的顺序相同。
3.如果两个字典的长度相同且它们的键值也完全匹配,则用字典中的每个相同的键所对应的值进行比较。
4.到此为止,每个字典的长度相同,键值相同,每个键对应的值也相同,则字典完全相同。
用工厂方法dict()从另一个字典生成一个新的字典时,新生成的字典是原来字典对象的浅拷贝。和列表类型的工厂方法list()一样。
另外采用工厂方法dict()生成新的字典的速度比用dict.copy()方法慢,推荐用dict.copy()方法
方法名字 | 操作 |
---|---|
dict.clear() | 删除字典中的所有元素 |
dict.copy() | 返回字典的一个浅拷贝副本 |
dict.fromkeys(seq,val=None) | 创建并返回一个新字典,以seq中的元素作为该字典的key,val做该字典中所有key的初始值 |
dict.get(key, default=None) | 返回字典中key对应的value,如果字典中不存在key,则返回default的值 |
dict.has_key(key) | 如果字典中存在key,则返回True,反之则返回False |
dict.items() | 返回一个包含字典中键-值对元组的列表 |
dict.keys() | 返回一个包含字典中键的列表 |
dict.iter*() | 方法iteritems(), iterkeys(), itervalues()与它们对应的非迭代方法一样,不同的是它们返回一个迭代器,而不是一个列表 |
dict.pop(key[,default]) | 和方法get()类似。如果字典中key存在,删除并返回key对应的值;如果key不存在,且没有给出default的值,则引发KeyError异常 |
dict.setdefault(key, default=None) | 和方法get()相似,如果字典中不存在key,则进行dict[key]=default赋值操作 |
dict.update(dict2) | 将字典dict2的键值对添加到字典dict中 |
dict.values() | 返回一个包含字典中所有值的列表 |
字典的内建方法
方法名字 | 操作 |
---|---|
dict.clear() | 删除字典中的所有元素 |
dict.copy() | 返回字典的一个浅拷贝副本 |
dict.fromkeys(seq,val=None) | 创建并返回一个新字典,以seq中的元素作为该字典的key,val做该字典中所有key的初始值 |
dict.get(key, default=None) | 返回字典中key对应的value,如果字典中不存在key,则返回default的值 |
dict.has_key(key) | 如果字典中存在key,则返回True,反之则返回False |
dict.items() | 返回一个包含字典中键-值对元组的列表 |
dict.keys() | 返回一个包含字典中键的列表 |
dict.iter*() | 方法iteritems(), iterkeys(), itervalues()与它们对应的非迭代方法一样,不同的是它们返回一个迭代器,而不是一个列表 |
dict.pop(key[,default]) | 和方法get()类似。如果字典中key存在,删除并返回key对应的值;如果key不存在,且没有给出default的值,则引发KeyError异常 |
dict.setdefault(key, default=None) | 和方法get()相似,如果字典中不存在key,则进行dict[key]=default赋值操作 |
dict.update(dict2) | 将字典dict2的键值对添加到字典dict中 |
dict.values() | 返回一个包含字典中所有值的列表 |
dict.update()方法,字典中原有的key和新添加的字典的key重复,那么重复的key对应的值将被新添加的字典的值给覆盖;
>>> dict1 = {'host': 'earth', 'post': 80}
>>> dict2 = {'host': 'venus', 'server': 'http'}
>>> dict1.update(dict2)
>>> dict1
{'server': 'http', 'post': 80, 'host': 'venus'}
字典的键必须是可哈希的!
所有不可变类型都是可哈希的,除了元组,元组只有在只包含数字和字符串这样的不可变类型时才可以作为字典中有效的key。
同时不是所有的可变对象都是不可哈希的,比如实现了__hash__()方法的类,只要__hash__()返回一个不可变类型,那么它就是一个可哈希的对象,可以用作字典的键。
集合是一组无序排列的可哈希的值,注意集合的元素都必须是可哈希的,所以list和dict不能作为集合的元素。
集合分成两种不同的类型,可变集合(set)和不可变集合(frozenset)。
可变集合可以添加或者删除元素,而不可变集合则不允许这么做。另外可变集合不可哈希,所以不能作为字典的key,但不可变集合是可哈希的,所以它可以作为字典的key。
函数/方法名 | 等价操作符 | 说明 |
---|---|---|
所有集合类型 | ||
len(s) | 集合长度,集合s中元素的个数 | |
set([obj]) | 可变集合工厂函数;obj必须是支持迭代的,由obj中的元素创建集合,否则创建一个空的集合 | |
frozenset([obj]) | 不可变集合工厂函数;和set()类似,但它返回的是一个不可变集合 | |
obj in s | 成员测试:obj是s中的一个元素吗? | |
obj not in s | 非成员测试:obj不是s中的一个元素吗? | |
s == t | 等价测试:测试s和t是否具有相同的元素? | |
s != t | 不等价测试: 与==相反 | |
s < t | (严格意义上)子集测试;s!=t而且s中所有的元素都是t的成员 | |
s.issubset(t) | s <= t | 子集测试(允许不严格意义上的子集):s中所有的元素都是t的成员 |
s > t | (严格意义上)超集测试:s!=t而且t中所有的元素都是s的成员 | |
s.issuperset(t) | s >= t | 超集测试(允许不严格意义上的超集):t中所有的元素都是s的成员 |
s.union(t) | s | t | 合并操作:s或者t中的元素 |
s.intersection(t) | s & t | 交集操作:s和t中的元素 |
s.difference(t) | s - t | 差分操作:s中的元素,而不是t中的元素 |
s.symmetric_difference(t) | s ^ t | 对称差分操作:s或t中的元素,但不是s和t共有的元素 |
s.copy() | 复制操作:返回s的浅拷贝副本 | |
仅用于可变集合 | ||
s.update(t) | s |= t | (Union)修改操作:将t中的成员添加到s |
s.intersection_update(t) | s &= t | 交集修改操作:s中仅包括s和t中共有的成员 |
s.difference_update(t) | s -= t | 差修改操作:s中包括仅属于s但不属于t的成员 |
s.symmetric_difference_update(t) | s ^= t | 对称差分修改操作:s中包括仅属于s或者仅属于t的成员 |
s.add(obj) | 加操作:将obj添加到s | |
s.remove(obj) | 删除操作:将obj从s中删除;如果s中不存在obj,将引发KeyError | |
s.discard(obj) | 丢弃操作:remove()的友好版本——如果s中存在obj,从s中删除它;如果obj不存在,也不会引发KeyError异常 | |
s.pop() | Pop操作:移除并返回s中的任意一个元素 | |
s.clear() | 清除操作:移除s中所有的元素 |
集合类型总结表
函数/方法名 | 等价操作符 | 说明 |
---|---|---|
所有集合类型 | ||
len(s) | 集合长度,集合s中元素的个数 | |
set([obj]) | 可变集合工厂函数;obj必须是支持迭代的,由obj中的元素创建集合,否则创建一个空的集合 | |
frozenset([obj]) | 不可变集合工厂函数;和set()类似,但它返回的是一个不可变集合 | |
obj in s | 成员测试:obj是s中的一个元素吗? | |
obj not in s | 非成员测试:obj不是s中的一个元素吗? | |
s == t | 等价测试:测试s和t是否具有相同的元素? | |
s != t | 不等价测试: 与==相反 | |
s < t | (严格意义上)子集测试;s!=t而且s中所有的元素都是t的成员 | |
s.issubset(t) | s <= t | 子集测试(允许不严格意义上的子集):s中所有的元素都是t的成员 |
s > t | (严格意义上)超集测试:s!=t而且t中所有的元素都是s的成员 | |
s.issuperset(t) | s >= t | 超集测试(允许不严格意义上的超集):t中所有的元素都是s的成员 |
s.union(t) | s | t | 合并操作:s或者t中的元素 |
s.intersection(t) | s & t | 交集操作:s和t中的元素 |
s.difference(t) | s - t | 差分操作:s中的元素,而不是t中的元素 |
s.symmetric_difference(t) | s ^ t | 对称差分操作:s或t中的元素,但不是s和t共有的元素 |
s.copy() | 复制操作:返回s的浅拷贝副本 | |
仅用于可变集合 | ||
s.update(t) | s |= t | (Union)修改操作:将t中的成员添加到s |
s.intersection_update(t) | s &= t | 交集修改操作:s中仅包括s和t中共有的成员 |
s.difference_update(t) | s -= t | 差修改操作:s中包括仅属于s但不属于t的成员 |
s.symmetric_difference_update(t) | s ^= t | 对称差分修改操作:s中包括仅属于s或者仅属于t的成员 |
s.add(obj) | 加操作:将obj添加到s | |
s.remove(obj) | 删除操作:将obj从s中删除;如果s中不存在obj,将引发KeyError | |
s.discard(obj) | 丢弃操作:remove()的友好版本——如果s中存在obj,从s中删除它;如果obj不存在,也不会引发KeyError异常 | |
s.pop() | Pop操作:移除并返回s中的任意一个元素 | |
s.clear() | 清除操作:移除s中所有的元素 |
对于集合类型操作符(|, &, -, ^)
如果左右两个操作数的类型相同,即都是可变集合或者不可变集合,则产生的结果类型是相同的,但如果左右两个操作数的类型不相同(左操作数是set,右操作数是frozenset,或者相反情况),则所产生的结果类型与左操作数相同。
>>> s = set([1,2,3])
>>> t = frozenset('abc')
>>> s ^ t
set({1, 2, 3, 'a', 'b', 'c'})
>>> t ^ s
frozenset({1, 2, 3, 'a', 'b', 'c'})