6.1一个简单的字典
来看一个游戏,其中包含一些外星人,这些外星人的颜色和点数各不相同,下面是一个简单的字典,存储了有关特定外星人的信息:
alien_0={'color':'green','points':5}
print (alien_0['color'])
print (alien_0['points'])
运行结果如下:
6.2使用字典
在python中,字典是一系列键-值对。每个键都与一个值相关联,你可以使用键来访问与之相关联的值。与键相关联的值可以是数字、字符串、列表乃至字典。事实上,可将任何python对象用作字典中的值。
在python中,字典用放在花括号{}中的一系列键-值对表示,如前面定示例所示:
键-值对是两个相关联的值。指定键时,python将返回与之相关联的值。键和值之间用冒号隔开,而键-值对之间是用逗号分隔。在字典中,你想存储多少个键-值对都可以。
6.2.1 访问字典中的值
要获取与键相关联的值,可一次指定字典名和放在方括号内的键,如下所示 :
现在,你可以访问外星人alien_0的颜色和点数。如果玩家射杀了这个外星人,你就可以使用下面的代码来确定玩家应获得多少个点:
alien_0={'color':'red','points':'5'}
new_points=alien_0['points']
print ("You just earned "+str(new_points)+'points!')
运行结果如下:
6.2.2 添加键-值对
字典是一种动态结构,可随时在其中添加键-值对。要添加键值对,可依次指定字典名、用方括号括起的键和相关联的值。
下面在字典alien_0中添加两项信息:外星人的x坐标和y坐标,让我们能够在屏幕的特定位置显示该外星人。我们将这个外星人放在屏幕左边缘,且离屏幕上边缘25像素的地方。由于屏幕坐标系的原点通常为左上角,因此要将该外星人放在屏幕左边缘,可将x坐标设置为0;要将该外星人放在离屏幕顶部25像素的地方,可将y坐标设置为25,如下所示:
alien_0={'color':'yellow','point':5}
print (alien_0)
alien_0['x_position']=0
alien_0['y_position']=25
print (alien_0)
运行结果如下:
6.2.3先创建一个空字典
有时候,在空字典中给添加键-值对是为了方便,而有时候必须这样做。为此,可先使用一对空的花括号定义一个字典,再分行添加键-值对。例如,下例演示了如何以这种方式创建字典alien_0:
alient_0={}
alient_0['color']='green'
alient_0['points']=5
alient_0['x_position']=0
alient_0['y_position']=25
print alient_0
运行结果如下:
使用字典来存储用户提供的数据或在编写能自动生成大量键-值对的代码时,通常都需要定义一个空字典。
6.2.4修改字典中的值
要修改字典中的值,可依次指定字典名、用方括号括起的键以及与该键相关联的新值。例如,假设随着游戏的进行,需要将一个外星人从绿色改为黄色:
alient_0={}
alient_0['color']='green'
alient_0['points']=5
alient_0['x_position']=0
alient_0['y_position']=25
print alient_0
alient_0['color']='yellow'
print alient_0
运行结果如下:
来看一个更有趣的例子:对一个能够以不同速度移动的外星人的位置进行跟踪。为此,我们将存储该外星人的当前速度,并据此确定该外星人将向右移动多远:
alien_0={'x_position':0,'y_position':25,'speed':'medium'}
print ("original x_position:"+str(alien_0['x_position']))
if alien_0['speed']=='slow':
x_increment=1
elif alien_0['speed']=='medium':
x_increment=2
else:
x_increment=3
alien_0['x_position']=alien_0['x_position']+x_increment
print ("New x-postion: "+str(alien_0['x_position']))
运行结果如下:
6.2.5删除键-值对
对于字典中不再需要的信息,可使用del语句将相应的键-值对彻底删除。使用del语句时,必须指定字典名和要删除的键。
例如,下面的代码从字典alien_0中删除键‘points’及其值:
alien_0={'color':'green','points':5}
print alien_0
del alien_0['point']
print alien_0
运行结果如下:
6.2.6由类似对象组成的字典
在前面的示例中,字典存储的是一个对象(游戏中的一个外星人)的多种信息,但你也可以使用字典来存储众多对象的同一种信息。例如,假设你要调查很多人,询问他们最喜欢的编程语言,可使用一个字典来存储这种简单调查的结果,给定被调查者的名字,可使用这个字典轻松地获悉他喜欢的语言,如下所示:
favorite_language={
'jen':'python',
'sarah':'c',
'edward':'ruby',
'phil':'python',
}
print ("sarah's favorite language is "+favorite_language['sarah'].title()+'.')
运行结果如下:
动手试一试
6-1 人:使用一个字典来存储一个熟人的信息,包括名、姓、年龄和居住的城市。该字典应包含键first_name、last_name、age和city。将存储在该字典中的每项信息都打印出来。
6-2 喜欢的数字:使用一个字典来储存一些人喜欢的数字。请想出5个人的名字,并将这些名字用作字典中的键;想出每个人喜欢的一个数字,并将这些数字作为值存储在字典中。打印每个人的名字和喜欢的数字。为让这个程序更有趣,通过询问朋友确保数据是真实的。
6-3 词汇表:Python字典可用于模拟现实生活中的字典,但为避免混淆,我们将后者称为词汇表。
想出你在前面学过的5个编程词汇,将它们用作词汇表中的键,并将它们的含义作为值存储在词汇中。
以整洁的方式打印每个词汇及其含义。为此,你可以先打印词汇,在它后面加上一个冒号,再打印词汇的含义;也可在一行打印词汇,再使用换行符(\n)
插入一个空行,然后在下一行以缩进的方式打印词汇的含义。
6.3 遍历字典
6.3.1遍历所有的键-值对
探索各种遍历方法前,先来看一个新字典,它用于存储有关网站用户的信息。下面的字典存储一名用户的用户名、名和姓。
user_0={
'username':'efermi',
'first':'enrico',
'last':'fermi',
}
如果要获悉该字典中的所有信息,可以使用一个for循环来遍历这个字典
items() 方法的遍历:items() 方法把字典中每对 key 和 value 组成一个元组,并把这些元组放在列表中返回。
for key,value in user_0.items():
print("\nkey:"+key)
print("\nvalue:"+value)
运行结果如下:
要编写用于遍历字典的for循环,可声明两个变量,用于存储键-值对中的键和值。对于这两个变量,可使用任何名称。
6.3.2 遍历字典中的所有键
在不需要字典中的值时,方法key()很有用。下面来遍历字典favorite_language,并将每个被调查者的名字都打印出来:
favorite_language={
'jen':'python',
'sarah':'c',
'edward':'ruby',
'phil':'python',
}
for name in favorite_language.keys(): #遍历字典时,会默认遍历所有的键
print (name.title())
运行结果如下:
python提取favorite_language中的所有键,并依次将它们存储到变量name中。输出列出了每个被调查者的名字
遍历字典时,会默认便利所有的键。因此,如果将上述代码中的for name infavorite_languages.key():替换为for name infavorite_languages(),输出将不变。
在这种循环中,可使用当前键来访问与之相关联的值。下面来打印两条消息,指出两位朋友喜欢的语言。我们像前面一样遍历字典中的名字,但在名字为指定朋友的名字时,打印一条消息,指出其喜欢的语言:
favorite_language={
'jen':'python',
'sarah':'c',
'edward':'ruby',
'phil':'python',
}
friends=['phil','sarah']
for name in favorite_language.keys():
print (name.title())
if name in friends:
print ("Hi "+name.title()+",I see your favorite language is "+favorite_language[name].title()+"!")
运行结果如下:
6.3.3按顺序遍历字典中的所有键
字典总是明确的记录键和值之间的关联关系,但获取字典的元素时,获取顺序是不可预测的。这不是问题,因为通常你想要的只是获取与键相关联的正确的值。
要以特定的顺序返回元素,一种办法是在for循环中对返回的键进行排序。为此,可使用函数sorted()来获的按特定顺序排列的键列表的副本:
favorite_language={
'jen':'python',
'sarah':'c',
'edward':'ruby',
'phil':'python',
}
for name in sorted(favorite_language):
print (name.title()+",thank you for taking the poll.")
运行结果如下:
6.3.4 遍历字典中的所有值
如果你感兴趣的主要是字典包含的值,可使用方法value(),它返回一个值列表,而不包含任何键。例如,如果我们想获得一个这样的列表,即其中只包含被调查者选择的各种语言,而不包含被调查者的名字,我们可以这样做:
favorite_language={
'jen':'python',
'sarah':'c',
'edward':'ruby',
'phil':'python',
}
print ("The following languages have been mentioned:")
for language in favorite_language.values():
print (language.title())
运行结果如下:
这种做法提取字典中所有的值,而没有考虑是否重复。涉及的值很少时,这也许不是问题,但如果被调查者很多,最终的列表可能包含大量的重复项。为剔除重复项,可使用集合(set)。集合类似于列表,但每个元素都必须是独一无二的:
favorite_language={
'jen':'python',
'sarah':'c',
'edward':'ruby',
'phil':'python',
}
print ("The fllowing languages have been mentioned:")
for v in set(favorite_language.values()):
print v.title()
运行结果如下:
动手试一试
6-4 词汇表2:既然你知道了如何遍历字典,现在请整理你为完成练习6-3而编写的代码,将其中的一系列print语句替换为一个遍历字典中的键和值得循环。确定该循环正确无误后,再在词汇表中添加5个python术语。当你再次运行这个程序时,这些新术语辑器含义将自动包含在输出中。
6-5河流:创建一个字典,在其中存储三条大河流及其流经得国家。其中一个键-值对可能是'nile':'egypt'
- 使用循环为每条和流打印一条消息,如“The Nile runs through Egypt”
- 使用循环将该字典中每条河流的名字都打印出来。
- 使用循环将该字典包含的每个国家的名字都打印出来。
6-6调查:在6.3.1节编写得程序favorite_languages中执行以下操作
- 创建一个应该会接受调查得人员名单,其中有些人已包含在字典中,而其他人未包含在字典中。
- 遍历这个人员名单,对于已参与调查得人,打印一条消息表示感谢。对于还未参与调查得人,打印一条消息邀请他参与调查。
6.4嵌套
有时候,需要将一系列字典存储在列表中,或将列表作为值存储在字典中,这称为嵌套。你可以在列表中嵌套字典、在字典中嵌套列表,甚至在字典中嵌套字典。
6.4.1 字典列表
字典alien_0包含一个外星人的各种信息,但无法存储第二个外星人的信息,更别说屏幕上全部外星人的信息了。如何管理成群结队的外星人呢?一种办法是创建一个外星人列表,其中每个外星人都是一个字典,包含有关该外星人的各种信息。例如,下面的代码创建一个包含三个外星人的列表:
cxr={'sex':'girl','name':'xr','age':'25',}
pty={'sex':'boy','name':'ty','age':'24',}
hf={'sex':'girl','name':'ff', 'age':'27'}
aliens=[cxr,pty,hf]
for alien in aliens:
print(alien)
运行结果如下:
更符合现实的情形是,外星人不止三个,且每个外星人都是使用代码自动生成的,在下面的示例中,我们使用range()生成了30个外星人:
aliens=[] #创建一个用于存储外星人的空列表
# 创建30个绿色的外星人
for alien_number in range(30):
new_alien={'color':'green','points':5,'speed':'slow'}
aliens.append(new_alien)
# 显示前5个外星人
for alien in aliens[:5]:
print (alien)
print ("Hello 5 aliens")
# 显示创建了多少个外星人
print ("Total number of aliens:"+str(len(aliens)))
# 要将前三个外星人修改为黄色的、速度为中等且值10个点,可以这样做:
for alien in aliens[0:3]:
if alien['color']=='green':
alien['color']='yellow'
alien['speed']='medium'
alien['point']=10
elif alien['color']=='yellow':
alien['color'] = 'red'
alien['speed'] = 'fast'
alien['point'] = 15
for alien in aliens[0:5]:
print (alien)
运行结果如下:
6.4.2 在字典中存储列表
例:你如何描述顾客点的比萨呢?在下面的示例中,存储了比萨的两方面信息:外皮类型和配料列表。其中的配料列表是一个与键‘toppings’相关联的值。要访问该列表,我们使用字典名和键‘toppings’,就像访问字典中的其他值一样。这将返回一个配料列表,而不是单个值:
# 存储所点比萨的信息
pizza={
'crust':'thick',
'toppings':['mushrooms','extra cheese'],
}
# 概述所点的比萨
print ("You ordered a "+pizza['crust']+'-crust pizza '+
"with the following toppings:")
for topping in pizza['toppings']:
print ("\t"+topping)
结果如下:
例:在最喜欢的编程语言的示例中 ,如果将每个人的回答都存储在一个列表中,被调查者就可以选择多种语言
favorite_languages={
'jen':['python','ruby'],
'sarah':['c'],
'edward':['ruby','go'],
'phil':['python','haskell'],
}
for name,languages in favorite_languages.items():
if len(languages)==1:
print ("\n"+name.title()+"'s favorite languages is:")
for language in languages:
print ("\t"+language.title())
else:
print ("\n" + name.title() + "'s favorite languages are:")
for language in languages:
print ("\t" + language.title())
运行结果如下:
为进一步改进这个程序,可在遍历字典的for循环开头添加一条if语句,通过查看len(language)的值来确定当前的被调查者喜欢的语言是否有多种,就像以前一样显示输出,如果只有一种,就相应修改输出的措辞,如显示Sarah’s favorite language is c.
6.4.3 在字典中存储字典
例如:如果有多个网站用户,每个都有独特得用户名,可在字典中将用户名作为键,然后将每位用户得信息存储在一个字典中,并将该字典作为与用户相关联得值。在下面得程序中,对于每位用户,我们都存储了其三项信息:名、姓和居住地;为访问这些信息,我们遍历所有得用户名,并访问与每个用户名相关联得信息字典:
users={
'cxr':{
'first':'xr',
'last':'c',
'location':'sx',
},
'hf':{
'first':'f',
'last':'h',
'location':'bj'
}
}
for username,user_info in users.items():
print ("\nUsername: "+username)
full_name=user_info['first']+" "+user_info['last']
location=user_info['location']
print ("\tFull name: "+full_name.title())
print ("\tLocation: "+location.title())
运行结果如下:
动手试一试
6-7 在为完成练习6-1而编写的程序中,再创建两个表示人的字典,然后将这三个字典都存储在一个名为people的列表中。遍历这个列表,将其中每个人的所有信息都打印出来。
6-8 宠物:创建多个字典,对于每个字典,都使用一个宠物的名称来给它命名;在每个字典中,包含宠物的类型及其主任得名字。将这些字典存储在一个名为pets的列表中,再便利该列表,并将宠物所有信息都打印出来。
6-9 喜欢的地方:创建一个名为favorite_palces的字典。在这个字典中,将三个人的名字用作键;对于其中的每个人,都存储他喜欢的1-3个地方,为让这个练习更有趣些,可让一些朋友指出他们喜欢的几个地方。便利这个字典,并将其中每个人的名字及其喜欢的地方打印出来。
6-10 喜欢的数字:修改为完成练习6-2而编写的程序,让每个人都可以有多个喜欢的数字,然后将每个人的名字及其喜欢的数字打印出来。
6-11 城市:创建一个名为cities的字典,其中将三个城市名用作键;对于每座城市,都创建一个字典,并在其中包含该城市所属的国家、人口约数以及一个有关该城市的事实。在表示每座城市的字典中,应包含每座城市的字典中,应包含country、population和fact等键。将每座城市的名字以及有关它们的信息都打印出来。