Python3中的生成器函數

目錄

1:生成器函數的定義

2:生成器函數的本質

3:小示例


    Python中對延遲提供了友好的支持:即它提供了在需要的時候才產生結果的工具,而不是立即產生結果。下面介紹的函數生成器就是這種工具之一。

1:生成器函數的定義

定義:使用常規的def語句進行編寫,但是使用yield語句一次返回一個結果集,在每次結果產生之間掛起和恢復它們的狀態。

# 常規函數
def func1():
	print('hello ')
	return 'ixusy88'

ret = func1()
print(ret)

'''
結果:
hello 
ixusy88
'''

print("*"*30)
# 生成器函數,把常規函數中的return替換爲yield
def func2():
	print('hello ')
	yield 'ixusy88'

ret = func2()  # 並沒有執行函數,而是返回一個生成器對象
print(ret)
'''
結果:
<generator object func2 at 0x00000244C40CEF10>
'''

2:生成器函數的本質

生成器函數本質就是一個迭代器:函數中如果包含一條yield語句,那麼Python就會將它編譯爲生成器,這個函數不再是普通函數,而是作爲返回支持迭代協議的對象的函數,這個函數返回的對象會自動創建名爲__next__的方法接口。

"""
yield語句會掛起該函數並向調用者傳回一個值,同時會保留足夠的狀態使
函數能從它離開的地方繼續執行,當繼續時,函數在上一個yield傳回後立即繼續執行。
"""
def func1(N):
	for i in range(N):
		yield i**2   

ret = func1(3)   # 只要函數func1中有yield語句,就會返回一個支持迭代協議的對象
print(ret)
print('__iter__' in dir(ret))
print('__next__' in dir(ret))

"""
輸出結果:
<generator object func1 at 0x000002636160EF68>
True
True
"""
print("*"*30)

# ret 是一個支持迭代協議的對象,可以通過手工進行訪問

print(ret.__next__())
print(ret.__next__())
print(ret.__next__())
print(ret.__next__())  #  

"""
0
1
4
Traceback (most recent call last):
  File "D:\python\生成器函數.py", line 53, in <module>
    print(ret.__next__())  #  StopIteration
StopIteration
"""



print("*"*30)
ret = func1(5) 
# ret 是一個支持迭代協議的對象,可以使用for循環來遍歷
for item in ret:
	print(item)
"""
0
1
4
9
16
"""

3:小示例
 

# 斐波那契函數
# 
def Fibonacci(N):
	a,b,max_cnt = 0,1,N
	while b <= max_cnt:
		a,b = b,a+b
		yield a 


print('*'*30)
fib = Fibonacci(5)
print(fib) 
for x in fib:
	print(x) 
'''
輸出結果:
<generator object Fibonacci at 0x000001A44C08EFC0>
1
1
2
3
5
'''
print('*'*30)

# 手工訪問
fib = Fibonacci(5)
print(fib.__next__())
print(fib.__next__())
print(fib.__next__())
print(fib.__next__())
print(fib.__next__())
print(fib.__next__())

'''
結果:
1
1
2
3
5
Traceback (most recent call last):
  File "D:\python\生成器函數.py", line 119, in <module>
    print(fib.__next__())
StopIteration

'''

 

 

 

 

 

 

 

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章