把一个字符串变成Unicode 码位的列表
symbols = '$¢£¥€¤'
codes = []
for symbol in symbols:
codes.append(ord(symbol))
使用列表推导,代码将非常简洁
symbols = '$¢£¥€¤'
codes = [ord(symbol) for symbol in symbols]
使用列表推导计算笛卡儿积
colors = ['black', 'white']
sizes = ['S', 'M', 'L']
tshirts = [(color, size) for color in colors for size in sizes]
for tshirt in tshirts:
print(tshirt)
('black', 'S')
('black', 'M')
('black', 'L')
('white', 'S')
('white', 'M')
('white', 'L')
列表推导的作用只有一个:生成列表。如果想生成其他类型的序列,生成器表达式就派上了用场。
虽然也可以用列表推导来初始化元组、数组或其他序列类型,但是生成器表达式是更好的选择。这是因为生成器表达式背后遵守了迭代器协议,可以逐个地产出元素,而不是先建立一个完整的列表,然后再把这个列表传递到某个构造函数里。前面那种方式显然能够节省内存。
用生成器表达式初始化元组和数组
symbols = '$¢£¥€¤'
# 如果生成器表达式是一个函数调用过程中的唯一参数,那么不需要额外再用括号把它围起来。
tuple(ord(symbol) for symbol in symbols)
import array
# array 的构造方法需要两个参数,因此括号是必需的。
array.array('I', (ord(symbol) for symbol in symbols))
下面使用生成器表达式计算笛卡儿积,与上面不同的是,用了生成器表达式后,内存里不会留下有6个组合的列表,因为生成器表达式会在每次for循环运行时才生成一个组合。
colors = ['black', 'white']
sizes = ['S', 'M', 'L']
for tshirt in ('{} {}'.format(color, size) for color in colors for size in sizes):
print(tshirt)
black S
black M
black L
white S
white M
white L
下面介绍元组,除了用作不可变的列表,它还可以用于没有字段名的记录。
把元组用作记录
lax_coordinates = (33.9425, -118.408056)
city, year, pop, chg, area = ('Tokyo', 2003, 32450, 0.66, 8014)
traveler_ids = [('USA', '31195855'), ('BRA', 'CE342567'), ('ESP', 'XDA205856')]
# 下面三者等效
for passport in traveler_ids:
print('{}/{}'.format(*passport))
for country, id in traveler_ids:
print(country, id , sep='/')
for passport in traveler_ids:
print('%s/%s' %s passport)
元组拆包
元组拆包可以应用到任何可迭代对象上,唯一的硬性要求是,被可迭代对象中的元素数量必须要跟接受这些元素的元组的空档数一致。除非我们用*
来表示忽略多余的元素。
一个很优雅的写法当属不使用中间变量交换两个变量的值
>>> b, a = a, b
下面用*
来处理剩下的元素
>>> a, b, *rest = range(5)
>>> a, b, rest
(0, 1, [2, 3, 4])
>>> a, b, *rest = range(3)
>>> a, b, rest
(0, 1, [2])
>>> a, b, *rest = range(2)
>>> a, b, rest
(0, 1, [])
嵌套元组拆包
接受表达式的元组可以是嵌套式的,例如(a, b, (c, d))。只要这个接受元组的嵌套结构符合表达式本身的嵌套结构,Python 就可以作出正确的对应。
metro_areas = [
('Tokyo','JP',36.933,(35.689722,139.691667)),
('Delhi NCR', 'IN', 21.935, (28.613889, 77.208889)),
('Mexico City', 'MX', 20.142, (19.433333, -99.133333)),
('New York-Newark', 'US', 20.104, (40.808611, -74.020386)),
('Sao Paulo', 'BR', 19.649, (-23.547778, -46.635833)),
]
print('{:15} | {:^9} | {:^9}'.format('', 'lat.', 'long.'))
fmt = '{:15} | {:9.4f} | {:9.4f}'
# 把输入元组的最后一个元素拆包到由变量构成的元组里,这样就获取了坐标
for name, cc, pop, (latitude, longitude) in metro_areas:
if longitude <= 0:
print(fmt.format(name, latitude, longitude))
| lat. | long.
Mexico City | 19.4333 | -99.1333
New York-Newark | 40.8086 | -74.0204
Sao Paulo | -23.5478 | -46.6358