Python異步之生成器怎么使用
本文講解"Python異步之生成器如何使用",希望能夠解決相關(guān)問題。
正文
生成器是 Python 的基本組成部分。生成器是一個(gè)至少有一個(gè)“yield”表達(dá)式的函數(shù)。它們是可以暫停和恢復(fù)的函數(shù),就像協(xié)程一樣。
實(shí)際上,Python 協(xié)程是 Python 生成器的擴(kuò)展。Asyncio 允許我們開發(fā)異步生成器。我們可以通過定義一個(gè)使用“yield”表達(dá)式的協(xié)程來創(chuàng)建一個(gè)異步生成器。
1. 什么是異步生成器
異步生成器是使用 yield 表達(dá)式的協(xié)程。在我們深入了解異步生成器的細(xì)節(jié)之前,讓我們先回顧一下經(jīng)典的 Python 生成器。
1.1. Generators
生成器是一個(gè) Python 函數(shù),它通過 yield 表達(dá)式返回一個(gè)值。
# define a generator def generator(): for i in range(10): yield i
生成器執(zhí)行到 yield 表達(dá)式,之后返回一個(gè)值。這會(huì)在該點(diǎn)暫停生成器。下一次執(zhí)行生成器時(shí),它將從恢復(fù)點(diǎn)恢復(fù)并運(yùn)行直到下一個(gè) yield 表達(dá)式。
從技術(shù)上講,生成器函數(shù)創(chuàng)建并返回一個(gè)生成器迭代器。生成器迭代器執(zhí)行生成器函數(shù)的內(nèi)容,根據(jù)需要產(chǎn)生和恢復(fù)。
可以使用內(nèi)置函數(shù) next() 分步執(zhí)行生成器。
... # create the generator gen = generator() # step the generator result = next(gen)
雖然,更常見的是迭代生成器直到完成,例如使用 for 循環(huán)或列表理解。
... # traverse the generator and collect results results = [item for item in generator()]
接下來,讓我們仔細(xì)看看異步生成器。
1.2. Asynchronous Generators
異步生成器是使用 yield 表達(dá)式的協(xié)程。與函數(shù)生成器不同,協(xié)程可以調(diào)度和等待其他協(xié)程和任務(wù)。
與經(jīng)典生成器一樣,異步生成器函數(shù)可用于創(chuàng)建可使用內(nèi)置的 anext() 函數(shù)而不是 next() 函數(shù)遍歷的異步生成器迭代器。
這意味著異步生成器迭代器實(shí)現(xiàn)了 anext() 方法并且可以與 async for 表達(dá)式一起使用。
這意味著生成器的每次迭代都被安排并執(zhí)行為可等待的。 “async for”表達(dá)式將調(diào)度并執(zhí)行生成器的每次迭代,暫停調(diào)用協(xié)程并等待結(jié)果。
2. 如何使用異步生成器
在本節(jié)中,我們將仔細(xì)研究如何在 asyncio 程序中定義、創(chuàng)建、步進(jìn)和遍歷異步生成器。
讓我們從如何定義異步生成器開始。
2.1. 定義
我們可以通過定義一個(gè)至少有一個(gè) yield 表達(dá)式的協(xié)程來定義一個(gè)異步生成器。
這意味著該函數(shù)是使用“async def”表達(dá)式定義的。
# define an asynchronous generator async def async_generator(): for i in range(10) yield i
因?yàn)楫惒缴善魇且粋€(gè)協(xié)程,并且每個(gè)迭代器返回一個(gè)在 asyncio 事件循環(huán)中調(diào)度和執(zhí)行的等待對(duì)象,所以我們可以在生成器主體內(nèi)執(zhí)行和等待等待對(duì)象。
# define an asynchronous generator that awaits async def async_generator(): for i in range(10) # suspend and sleep a moment await asyncio.sleep(1) # yield a value to the caller yield i
接下來,讓我們看看如何使用異步生成器。
2.2. 創(chuàng)建
要使用異步生成器,我們必須創(chuàng)建生成器。這看起來像是調(diào)用它,而是創(chuàng)建并返回一個(gè)迭代器對(duì)象。
... # create the iterator it = async_generator()
這將返回一種稱為異步生成器迭代器的異步迭代器。
2.3. 一步
可以使用 anext() 內(nèi)置函數(shù)遍歷生成器的一個(gè)步驟,就像使用 next() 函數(shù)的經(jīng)典生成器一樣。
結(jié)果是等待的可等待對(duì)象。
... # get an awaitable for one step of the generator awaitable = anext(gen) # execute the one step of the generator and get the result result = await awaitable
這可以一步實(shí)現(xiàn)。
... # step the async generator result = await anext(gen)
2.4. 遍歷
還可以使用“async for”表達(dá)式在循環(huán)中遍歷異步生成器,該表達(dá)式將自動(dòng)等待循環(huán)的每次迭代。
... # traverse an asynchronous generator async for result in async_generator(): print(result)
我們還可以使用帶有“async for”表達(dá)式的異步列表理解來收集生成器的結(jié)果。
... # async list comprehension with async generator results = [item async for item in async_generator()]
3. 異步生成器示例
我們可以探索如何使用“async for”表達(dá)式遍歷異步生成器。
在此示例中,我們將更新之前的示例以使用“async for”循環(huán)遍歷生成器直至完成。
此循環(huán)將自動(dòng)等待從生成器返回的每個(gè)可等待對(duì)象,檢索產(chǎn)生的值,并使其在循環(huán)體內(nèi)可用,以便在這種情況下可以報(bào)告它。
這可能是異步生成器最常見的使用模式。
# SuperFastPython.com # example of asynchronous generator with async for loop import asyncio # define an asynchronous generator async def async_generator(): # normal loop for i in range(10): # block to simulate doing work await asyncio.sleep(1) # yield the result yield i # main coroutine async def main(): # loop over async generator with async for loop async for item in async_generator(): print(item) # execute the asyncio program asyncio.run(main())
運(yùn)行示例首先創(chuàng)建 main() 協(xié)程并將其用作 asyncio 程序的入口點(diǎn)。main() 協(xié)程運(yùn)行并啟動(dòng) for 循環(huán)。
異步生成器的一個(gè)實(shí)例被創(chuàng)建,循環(huán)使用 anext() 函數(shù)自動(dòng)單步執(zhí)行它以返回一個(gè)可等待對(duì)象。然后循環(huán)等待可等待對(duì)象并檢索一個(gè)值,該值可用于報(bào)告它的循環(huán)體。
然后重復(fù)此過程,掛起 main() 協(xié)程,執(zhí)行生成器的迭代,然后掛起和恢復(fù) main() 協(xié)程,直到生成器耗盡。
這突出顯示了如何使用 async for 表達(dá)式遍歷異步生成器。
0
1
2
3
4
5
6
7
8
9
關(guān)于 "Python異步之生成器如何使用" 就介紹到此。希望多多支持碩編程。
- python中f字符串以及其常見用法介紹
- Python的gtts庫(kù)將文字轉(zhuǎn)為音頻應(yīng)該如何操作
- 在Python里面調(diào)用Golang代碼的方法
- Python?Pyperclip模塊怎么安裝和使用
- Python異步之怎么保護(hù)任務(wù)免于取消
- python中的Pyperclip模塊功能是什么
- Python反射機(jī)制怎么應(yīng)用
- Python錯(cuò)誤JSONDecodeError:?Expecting?value:?line?1?column?1怎么解決
- Python數(shù)據(jù)可視化之Pyecharts如何使用
- Python HTTP請(qǐng)求
- Python HTTP響應(yīng)
- Python 連接重用
- Python Telnet
- Python 電子郵件
- Python POP3
- Python 并發(fā)簡(jiǎn)介
- Python 系統(tǒng)和內(nèi)存架構(gòu)
- Python 線程
- Python 線程通信
- Python 反應(yīng)式編程