上QQ阅读APP看书,第一时间看更新
4.1.4 反向迭代
在实际应用中,将一个序列逆序输出是比较常见的操作。对于迭代,这种操作称为反方向迭代。
对于反向迭代序列,我们可以使用内置的reversed()函数,代码(reversed_iter.py)如下:
a = [1, 2, 3, 4] print(f'primary a is: {a}') b = list() for x in reversed(a): b.append(x) print(f'{a} reversed is: {b}')
执行py文件,输出结果如下:
primary a is: [1, 2, 3, 4] [1, 2, 3, 4] reversed is: [4, 3, 2, 1]
反向迭代仅仅当对象的大小可预先确定或者对象实现了__reversed__()函数才生效。如果两者都不符合,必须先将对象转换为一个列表,代码如下:
f = open('/etc/passwd') for line in reversed(list(f)): print(line, end='')
注意 如果可迭代对象元素很多,将其预先转换为一个列表要消耗大量的内存。
我们可以通过在自定义类上实现__reversed__()方法来实现反向迭代,代码(reversed_iter.py)示例如下:
class Countdown: def __init__(self, start): self.start = start # Forward iterator def __iter__(self): n = self.start while n > 0: yield n n -= 1 # Reverse iterator def __reversed__(self): n = 1 while n <= self.start: yield n n += 1 for rev_val in reversed(Countdown(20)): print(f'reversed order: {rev_val}') print() for nor_val in Countdown(20): print(f'normal order: {nor_val}')
执行py文件,输出结果如下:
reversed order: 1 reversed order: 2 ... reversed order: 20 normal order: 20 normal order: 19 ... normal order: 1
定义一个反向迭代器可以使代码运行非常高效,因为不再需要将数据填充到一个列表中,然后再去反向迭代该列表。