Python迭代器與生成器

2018-06-08 17:18 更新

生成器

僅僅擁有生成某種東西的能力,如果不用__next__方法是獲取不到值得。


創(chuàng)建一個生成器函數(shù)

>>> def scq():
...    print("11")
# 當(dāng)函數(shù)代碼塊中遇到y(tǒng)ield關(guān)鍵字的時候,這個函數(shù)就是一個生成器函數(shù)
...    yield 1
...    print("22")
...    yield 2
...    print("33")
...    yield 3
...

把生成器賦值給一個對象

>>> r = scq()

查看r的蘇劇類型并且輸出r的值

>>> print(type(r),r)
<class 'generator'> <generator object scq at 0x000001F117D8DF10>

當(dāng)執(zhí)行生成器的__next__的時候,代碼會按照順序去執(zhí)行,當(dāng)執(zhí)行到yield時會返回并提出,yield后面的值就是返回值,然后記錄代碼執(zhí)行的位置,并退出

>>> ret = r.__next__()
11

第二次執(zhí)行的時候會根據(jù)上次代碼執(zhí)行的位置繼續(xù)往下執(zhí)行

>>> ret = r.__next__()
22
>>> ret = r.__next__()
33

如果__next__獲取不到值的時候就會報StopIteration錯誤

>>> ret = r.__next__()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  StopIteration

利用生成器創(chuàng)建一個類似xrange的功能

代碼

# 創(chuàng)建一個生成器函數(shù),函數(shù)名是range,n是傳入的參數(shù),也是輸出的數(shù)的最大值
def range(n):
    # 默認(rèn)從0開始    
    start = 0    
    # 進(jìn)入while循環(huán),如果最小值小于最大值就進(jìn)入循環(huán)    
    while start < n:        
    # 第一次返回start,下面代碼不執(zhí)行        
    yield start        
    # 第二次進(jìn)來的時候start = start + 1,然后進(jìn)入下一次循環(huán)        
    start += 1
    # 停止的參數(shù)為5
    obj = range(5)
    # 第一個數(shù)賦值給n1
    n1 = obj.__next__()
    # 第二個數(shù)賦值給n2
    n2 = obj.__next__()
    # 第三個數(shù)賦值給n3
    n3 = obj.__next__()
    # 第四個數(shù)賦值給n4
    n4 = obj.__next__()
    # 第五個數(shù)賦值給n5
    n5 = obj.__next__()
    # 輸出這五個數(shù)的值
    print(n1,n2,n3,n4,n5)

執(zhí)行結(jié)果

C:\Python35\python.exe F:/Python_code/sublime/Week5/Day03/s1.py
0 1 2 3 4

Process finished with exit code 0

迭代器

具有訪問生成器的能力,可以訪問到生成器的值,類似于生成器的__next__方法,一個一個值一個值得去迭代,只能夠按照順序的去查找。

特點:

  1. 訪問者不需要關(guān)心迭代器內(nèi)部的結(jié)構(gòu),僅需通過next()方法不斷去取下一個內(nèi)容

  2. 不能隨機(jī)訪問集合中的某個值 ,只能從頭到尾依次訪問

  3. 訪問到一半時不能往回退

  4. 便于循環(huán)比較大的數(shù)據(jù)集合,節(jié)省內(nèi)存

優(yōu)化上面rangexrange的生成器

def irange(start, stop, step=1):    
while start != stop:
        yield start
        start += step    
        else:        
        raise StopIteration
        for n in irange(1, 10):
            """for循環(huán)只要遇到StopIteration就會停止"""    
            print(n)ret = irange(1, 20)
            print(ret)  # 返回一個生成器,相當(dāng)于只在內(nèi)存中創(chuàng)建了一個值
            print(list(ret))  # 如果想要得到全部的值,變成列表就可以
  1. /Library/Frameworks/Python.framework/Versions/3.5/bin/python3.5 /Users/ansheng/MyPythonCode/hello.py

  2. 1

  3. 2

  4. 3

  5. 4

  6. 5

  7. 6

  8. 7

  9. 8

  10. 9

  11. <generator object irange at 0x1021df7d8>

  12. [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19]

  13. Process finished with exit code 0


本文出自 “一盞燭光” 博客,謝絕轉(zhuǎn)載!

以上內(nèi)容是否對您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號
微信公眾號

編程獅公眾號