python核心编程第二版第七章学习笔记

一. 映射类型:字典
字典是Python 语言中唯一的映射类型。映射类型对象里哈希值(键) 和指向的对象(值)是一对 多的关系。

映射类型不要求用数字值做索引以从一个容器中获 取对应的数据项。你可以用键(key)直接 "映射" 到值, 这就是为什么叫映射类型(“mapping type”) 的原因。映射类型通常被称做哈希表的原因是字典对象就是哈希类型的。字典是Python 中最强大的 数据类型之一。
1.核心笔记:什么是哈希表?它们与字典的关系是什么?
  哈希表(Hash table,也叫散列表),是根据关键码值(Key value)而直接进行访问的数据结构。也就是说,它通过把关键码值映射到表中一个位置来访问记录,以加快查找的速度。这个映射函数叫做散列函数,存放记录的数组叫做散列表。
序列类型用有序的数字键做索引将数据以数组的形式存储。一般,索引值与所存储的数据毫无 关系。还可以用另一种方式来存储数据:基于某种相关值,比如说一个字符串。我们在日常生活中 一直这么做。你把人们的电话号码按照他们的姓记录在电话簿上,你按照时间在日历或约会簿上添 加事件,等等。在这些例子中,你的键(key)就是和数据项相关的值。 哈希表是一种数据结构: 它按照我们所要求的去工作。哈希表中存储的每一条数据,叫做一个 值(value),是根据与它相关的一个被称作为键(key)的数据项进行存储的。键和值合在一起被称为 “键-值 对”(key-value pairs)。 哈希表的算法是获取键, 对键执行一个叫做哈希函数的操作, 并根据计算的结果,选择在数据结构的某个地址中来存储你的值。任何一个值存储的地址皆取决于
它的键。正因为这种随意性, 哈希表中的值是没有顺序的。你拥有的是一个无序的数据集。 你所能获得的有序集合只能是字典中的键的集合或者值的集合。 方法Keys() 或 values() 返回 一个列表,该列表是可排序的。 你还可以用 items()方法得到包含键、值对的元组的列表来排序。 由于字典本身是哈希的,所以是无序的。 哈希表一般有很好的性能, 因为用键查询相当快。
2.如何创建字典和给字典赋值
(1)可以用工厂方法 dict() 来创建字典。

>>> fdict = dict((['x', 1], ['y', 2]))
>>> fdict
{'y': 2, 'x': 1}

(2) 用内建方法fromkeys() 来创建一个"默认"字典
 字 典中元素具有相同的值 (如果没有给出, 默认为None):
>>> ddict = {}.fromkeys(('x', 'y'), -1)
>>> ddict
{'y': -1, 'x': -1}
>>> edict = {}.fromkeys(('foo', 'bar'))
>>> edict
{'foo': None, 'bar': None}

3. 如何访问字典中的值
用迭代器来轻松地访问类序列对象(sequence-like objects),比如字典和文件。只需要用字 典的名字就可以在 for 循环里遍历字典。

>>> dict2 = {'name': 'earth', 'port': 80}
>>>
>>>> for key in dict2:
... print 'key=%s, value=%s' % (key, dict2[key])
...
key=name, value=earth
key=port, value=80

字典中的键不能改变, 因此必须是可哈希 的, 所以数字和字符串可以作为字典中的键, 但是列表和其他字典不行。
4. 如何更新字典
你可以通过以下几种方式对一个字典做修改:添加一个新数据项或新元素(即,一个键-值对); 修改一个已存在的数据项;或删除一个已存在的数据项(下面有关于数据项删除操作的详细讲述).

>>> dict2['name'] = 'venus' # 更新已有条目
>>> dict2['port'] = 6969 # 更新已有条目
>>> dict2['arch'] = 'sunos5'# 增加新条目
5.如何删除字典元素和字典
删除整个字典的操作不常见。通常,你删除字典中的单个元素或是清除整个字典的内容。但是, 如果你真想"删除"一个字典,用del 语句 (介绍见小节 3.5.5)。 以下是删除字典和字典元素的例 子。

del dict2['name'] # 删除键为“name”的条目
dict2.clear() # 删除dict2 中所有的条目
del dict2 # 删除整个dict2 字典
dict2.pop('name') # 删除并返回键为“name”的条目
核心笔记:避免使用内建对象名字作为变量的标识符
6.*字典比较算法
cmp()可以返回除-1,0,1 外的其他值。算法按照以下的顺序。
( 1)比较字典长度
如果字典的长度不同,那么用 cmp(dict1, dict2) 比较大小时,如果字典 dict1 比 dict2 长, cmp()返回正值,如果 dict2 比 dict1 长,则返回负值。也就是说,字典中的键的个数越多,这个 字典就越大,即:
len(dict1) > len(dict2) ==> dict1 > dict2
(2)比较字典的键
如果两个字典的长度相同,那就按字典的键比较;键比较的顺序和 keys()方法返回键的顺序相 同。 (注意: 相同的键会映射到哈希表的同一位置,这保证了对字典键的检查的一致性。) 这时, 如果两个字典的键不匹配时,对这两个(不匹配的键)直接进行比较。当dict1 中第一个不同的键大 于dict2 中第一个不同的键,cmp()会返回正值。
( 3)比较字典的值
如果两个字典的长度相同而且它们的键也完全匹配,则用字典中每个相同的键所对应的值进行 比较。一旦出现不匹配的值,就对这两个值进行直接比较。若dict1 比dict2 中相同的键所对应的 值大,cmp()会返回正值。
(4) Exact Match
到此为止,即,每个字典有相同的长度、相同的键、每个键也对应相同的值,则字典完全匹配, 返回0 值。
7. 映射类型相关的函数
(1)内建方法
函数                        操作
dict([container])  创建字典的工厂函数。如果提供了容器类(container),就 用其中的条目填充字典,否则就创建一个典。
len(mapping)       返回映射的长度(键-值对的个数)
hash(obj)          返回obj 的哈希值
dict()
工厂函数被用来创建字典。如果不提供参数,会生成空字典。当容器类型对象做为一个参数传 递给方法dict() 时很有意思。如果参数是可以迭代的,即,一个序列,或是一个迭代器,或是一个 支持迭代的对象,那每个可迭代的元素必须成对出现。 在每个值对中,第一个元素是字典的键、第 二个元素是字典中的值。

>>> dict(zip(('x', 'y'), (1, 2)))
{'y': 2, 'x': 1}
>>> dict([['x', 1], ['y', 2]])
{'y': 2, 'x': 1}
>>> dict([('xy'[i-1], i) for i in range(1,3)])
{'y': 2, 'x': 1}

如果输入参数是(另)一个映射对象 ,比如,一个字典对象,对其调用dict()会从存在的字典里 复制内容来生成新的字典。 新生成的字典是原来字典对象的 浅复制版本 它与用字典的内建方法 copy() 生成的字典对象是一样的。但是从已存在的字典生成新的字典速度比用copy()方法慢,我们 推荐使用copy()。

>>> dict(x=1, y=2)
{'y': 2, 'x': 1}
>>> dict8 = dict(x=1, y=2)
>>> dict8
{'y': 2, 'x': 1}
>>> dict9 = dict(**dict8)
>>> dict9
{'y': 2, 'x': 1}

使用下面这 些行的方法更聪明(效率更好):

>>> dict9 = dict8.copy()
>>> dict9
{'y': 2, 'x': 1}

(2) 字典类型方法
方法名字                     操作
dict.clear a ()                删除字典中所有元素
dict.copy a ()                 返回字典(浅复制)的一个副本
dict.fromkeys c (seq, val=None)   创建并返回一个新字典,以seq 中的元素做该字典的键,val 做该字 典中所有键对应的初始值 (如果不提供此值,则默认为None)
dict.get(key, default=None) a      对字典dict 中的键key,返回它对应的值value,如果字典中不存在此 键,则返回default 的值 (注意,参数default 的默认值为None)
dict.has_key(key)            如果键(key)在字典中存在,返回True,否则返回False. 
dict.items()                 返回一个包含字典中(键, 值)对元组的列表
dict.keys()                  返回一个包含字典中键的列表
dict.iter() d                                    方法iteritems(), iterkeys(), itervalues()与它们对应的非迭代方法 一样,不同的是它们 返回一个迭代子,而不是一个列表。
dict.pop c (key [, default])         和方法get()相似,如果字典中key 键存在,删除并返回dict[key], 如果key 键不存在,且没有给出default 的值,引发KeyError 异常。
dict.setdefault(key, default=None)      和方法set()相似,如果字典中不存在key 键,由dict[key]=default 为 它赋值。
dict.update(dict2)                         将字典dict2 的键-值对添加到字典
dict dict.values()             返回一个包含字典中所有值的列表

>>> myDict = {'host': 'earth', 'port': 80}
>>> myDict.keys()
['host', 'port']
>>> myDict.items()
[('host', 'earth'), ('port', 80)]
>>> myDict.setdefault('port', 8080)
80
>>> myDict.setdefault('prot', 'tcp')
'tcp'
>>> myDict.items()
[('prot', 'tcp'), ('host', 'earth'), ('port', 80)]
>>> {}.fromkeys('xyz')
{'y': None, 'x': None, 'z': None}
>>>
>>> {}.fromkeys(('love', 'honor'), True)
{'love': True, 'honor': True}

(3) 字典的键
字典中的值没有任何限制。 他们可以是任意Python 对象,即,从标准对象到用户自定义对象 皆可。但是字典中的键是有类型限制的。
a.不允许一个键对应多个值
b. 键必须是可哈希的


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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值