標籤:std 運算式 cond 因此 計算 儲存 def return 結束
generator
產生器generator:一邊迴圈一邊計算的機制。
產生器是一個特殊的程式,可以被用於控制迴圈的迭代行為。python中的產生器是迭代器的一種,使用yield傳回值函數,每次調用yield會暫停,可以使用next()函數和send()函數恢複產生器。
產生器類似於傳回值為數組的一個函數,這個函數可以接受參數,可以被調用。但是,不同於一般函數會一次性返回包括了所有數值的數組,產生器一次只能產生一個值,這個消耗的記憶體數量將大大減小。因此,產生器看起來像是一個函數,但是表現得像迭代器。
建立generator方法一:產生器運算式
產生器運算式:返回一個對象,這個對象只有在需要的時候才產生結果。
只要把一個列表產生式中的[]改為(),就建立一個generator。
>>> list(x*x for x in range(5))[0, 1, 4, 9, 16]>>> list[x*x for x in range(5)] File "<stdin>", line 1 list[x*x for x in range(5)] ^SyntaxError: invalid syntax>>> #列表解析產生列表... [ x**3 for x in range(5)][0, 1, 8, 27, 64]>>> #產生器運算式... ( x**3 for x in range(5))<generator object <genexpr> at 0x105d8ba50>>>> list( x**3 for x in range(5))[0, 1, 8, 27, 64]
方法二:產生器函數
也是用def定義,如果一個函數至少包含一個yield聲明(當然它也可以包含其他yield或return),那麼它就是一個generator.
yield和return都會讓函數返回一些東西,區別在於,return聲明徹底結束一個函數,而yield聲明是暫停函數,儲存它的所有狀態,並且後續被調用後會繼續執行。
>> def my_gen():... n=1... print "first"... yield n... n+=1... print "second"... yield n... >>> for item in my_gen():... print item... first1second2>>
一個迭代可以被寫成產生器函數,也可以被寫成產生器運算式,均支援自動和手動迭代。而且這些產生器只支援一個active迭代,也就是產生器的迭代器就是產生器本身。
迭代器(迭代就是迴圈)
可以直接作用於for迴圈的資料類型:
- 集合資料類型,如list、tuple、dict、set、str
- generator,包括產生器函數和運算式?
- 這些可以直接作用於for迴圈對象的統稱為可迭代對象:Iterable
- 可以被next()函數調用並不斷返回下一個值的對象成為迭代器:Iterator
- 產生器都是Iterator對象,但list、dict、str雖然是Iterable(可迭代對象),卻不是Iterator(迭代器)。
- 把list、dict、str等Iterable變成Iterator可以使用iter()函數。
Iterator對象表示的是一個資料流,Iterator對象可以被next()函數調用並不斷返回下一個資料,直到沒有資料時拋出StopIteration錯誤。可以把這個資料流看做是一個有序序列,但我們卻不能提前知道序列的長度,只能不斷通過next()函數實現按需計算下一個資料,所以Iterator的計算是惰性的,只有在需要返回下一個資料時它才會計算。
小結
- 凡是可作用於for迴圈的對象都是Iterable類型;
- 凡是可作用於next()函數的對象都是Iterator類型,它們表示一個惰性計算的序列;
- 集合資料類型如list、dict、str等是Iterable但不是Iterator,不過可以通過iter()函數獲得一個Iterator對象。
Python之產生器(generator)和迭代器(Iterator)