[2021 Spring] CS61A 学习笔记 lecture 15 Iterators + Generators

主要内容:迭代器和生成器

Iterators

An iterator is an object that provides sequential access to values, one by one.

  • iter(iterable) returns an iterator over the elements of an iterable.
  • next(iterator) returns the next element in an iterator.

Iterators vs. For loops

一般情况下使用for循环进行迭代,除非有特殊理由需要用到next() / iter() / StopIteration, for循环易读也更优化。
迭代器:

ranked_chocolates = ("Dark", "Milk", "White")
chocorator = iter(ranked_chocolates)
try :
whileTrue:
        choco = next(chocorator)
        print(choco)
except StopIteration:
    print("No more left!")

for 循环(其实是一种语法糖)

ranked_chocolates = ("Dark", "Milk", "White")
for  chocolate in ranked_chocolates:
    print(chocolate)

Functions that return iterators

返回迭代器的函数有:reversed(sequence), zip(*iterables), map(func, iterable, ...), filter(func, iterable)

Bonus 1:生成迭代器后,修改iterable的值是很危险的

使用reversed生成迭代器后,

  1. 在原列表后添加元素,迭代器不会添加。
  2. 修改原列表中的值,迭代器返回值也会被修改,但是不会重新排序。
  3. list(iterator)会生成新的列表,原列表中值的变化不会改变新列表的值。

Generators

A generator is a type of iterator that yields results from a generator function.

How generators work

Looping over generators

生成器是一种特殊的迭代器。

Why use generators?

只需要少量元素时,使用生成器相比生成整个序列可以节省很大的空间。

Yielding from iterables

def a_then_b (a, b):
    yield from a
    yield from b
list(a_then_b(["Apples" , "Aardvarks"], ["Bananas", "BEARS"]))

Recursive yield from

def factorial(n, accum):
    if n == 0:
        yield accum
    else:
        yield from factorial(n - 1, n * accum)

for num in factorial(3, 1):
    print(num)

Recursive generators for trees

def leaves(t):
    yield label(t)
    for c in branches(t):
        yield from leaves(c)
t = tree(20, [tree( 12,
               [tree(9,
                  [tree(7), tree( 2)]),
                tree(3)]),
              tree(8,
               [tree(4), tree( 4)])])
leave_gen = leaves(t)
next(leave_gen)
posted @ 2021-07-01 20:59  ikventure  阅读(331)  评论(0编辑  收藏  举报