python 基礎——generate生成器


通過列表表達式可以直接生成列表,不過列表一旦生成就需要為所有元素分配內存,有時候會很消耗資源。

所以,如果列表元素可以按照某種算法推算出來,這樣就不必創建完整的list,從而節省大量的內存空間。

在Python中,這種一邊循環一邊計算的機制,稱為生成器(Generator)。

創建列表

法一:
test = range(10)
print type(test)
# <type 'list'>

法二:
test = [item for item in range(10)]
print type(test)
# <type 'list'>

創建生成器

test = (item for item in range(10))
print type(test)
# <type 'generator'>

生成器是一個可以自動推導后續元素的對象,為了得到其元素,我們可以直接通過 next() 方法:

test = (item for item in range(10))
print type(test)
print test.next()
print test.next()
print test.next()
# <type 'generator'>
# 0
# 1
# 2

另外一種方式是用 for 可以直接迭代生成器的所有元素:

test = (item for item in range(10))
print type(test)
for item in test:
    print item
# <type 'generator'>
# 0
# 1
# 2
# 3
# 4
# 5
# 6
# 7
# 8
# 9

注意,每一次調用 next() 都使得生成器推導出下一個元素,使得生成器的元素減少:

test = (item for item in range(10))
print type(test)
print test.next()
print test.next()
#至此,生成器中只還有8個元素
for index, item in enumerate(test):
    print index, '=', item
# <type 'generator'>
# 0
# 1
# 0 = 2
# 1 = 3
# 2 = 4
# 3 = 5
# 4 = 6
# 5 = 7
# 6 = 8
# 7 = 9

用函數創建生成器

如果函數中包含 yield ,那么該函數就變成了一個生成器。

函數類型的生成器的特點是:在每次調用 next() 的時候執行,遇到 yield 語句就完成一個元素的推導並返回,再次執行 next() 時從上次返回的 yield 語句處繼續向后執行:

def func():                       def func():
    print 'one'                       print 'one'
    yield 1                           yield 1
    print 'two'                       print 'two'
    yield 2                           yield 2
    print 'three'                     print 'three'
    yield 3                           yield 3

test = func()                     test = func()
test.next()                       test.next()
test.next()                       test.next()

for item in test:                 for item in test:
    print item                        item

# one                              # one
# two                              # two
# three                            # three
# 3                                #            此時並沒有打印生成器的最后一個元素值

生成器函數應用示例

用生成器產生斐波拉契數列(Fibonacci),除第一個和第二個數外,任意一個數都可由前兩個數相加得到:

直接打印元素:

def func(max):
    before = 0
    after = 1
    while after < max:
        print before
        before, after = after, before + after
        
func(10)
# 0
# 1
# 1
# 2
# 3
# 5

使用列表保存結果:

def func(max):
    list = []
    before = 0
    after = 1
    
    while after < max:
        list.append(before)
        before, after = after, before + after
    return list
        
my_list = func(10)
print my_list

# [0, 1, 1, 2, 3, 5]

使用生成器:

def func(max):
    before = 0
    after = 1
    while after < max:
        yield before
        before, after = after, before + after
        
test = func(10)
print test
for item in test:
    print item

# <generator object func at 0x7f228e111730>
# 0
# 1
# 1
# 2
# 3
# 5

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM