日本免费高清视频-国产福利视频导航-黄色在线播放国产-天天操天天操天天操天天操|www.shdianci.com

學無先后,達者為師

網站首頁 編程語言 正文

Python?asyncio異步編程常見問題小結_python

作者:永遠是少年啊 ? 更新時間: 2023-03-16 編程語言

今天繼續給大家介紹Python相關知識,本文主要內容是Python asyncio異步編程常見問題。

一、asyncio編程簡單示例

首先,我們來看一段簡單的Python asyncio異步編程代碼,相關代碼如下所示:

import asyncio

async def fun():
    print(1)
    await asyncio.sleep(2)
    print(2)
    return 3

async def main():
    task_list=[
        asyncio.create_task(fun()),
        asyncio.create_task(fun())
    ]
	done,pending=await asyncio.wait(task_list)
    print(done)
asyncio.run(main())

在上述代碼中,我們使用了Task列表,將兩個fun()協程函數生成的Task對象添加到task列表中,最終實現了這兩個函數異步執行。上述代碼執行結果如下所示:

二、asyncio編程常見問題

下面,我們想要簡單的修改一下上述代碼,我們把main()函數刪除,嘗試直接生成協程對象列表,結果如下所示:

import asyncio

async def fun():
    print(1)
    await asyncio.sleep(2)
    print(2)
    return 3

task_list=[
    asyncio.create_task(fun()),
    asyncio.create_task(fun())
]

done,pending=asyncio.run(asyncio.wait(task_list))
print(done)

上述代碼執行結果如下所示:

三、報錯原因及解決方案

從上圖中可以看出,上述代碼執行報錯,錯誤提示為:RuntimeError:no running event loop。
其實,之所以出現上述報錯,直接原因在于當前沒有事件循環。當我們使用asyncio模塊來實現異步編程時,asyncio模塊的優點在于省略了我們創建事件循環的過程,但是這并不意味著asyncio異步編程不需要事件循環。事實上,在第一段代碼中,代碼:

asyncio.run(main())

在實際上創建了這個事件循環,但是asyncio模塊屏蔽了這一細節。而正是因為已經存在了事件循環,因此我們才可以執行命令:

done,pending=await asyncio.wait(task_list)

但是在上述代碼中,我們沒有創建事件循環,而是直接將該代碼放到主程序中執行,因此上述代碼會出現報錯。
針對上述代碼,我們可以簡單修改為以下內容:

import asyncio

async def fun():
    print(1)
    await asyncio.sleep(2)
    print(2)
    return 3

task_list=[
    fun(),
    fun()
]

done,pending=asyncio.run(asyncio.wait(task_list))
print(done)

在上述代碼中,我們的Task列表中存放的是協程對象,而不是Task對象,這樣,我們在執行asyncio.wait時會自動創建一個事件循環,并且把協程對象加入到事件循環中。因此上述代碼也就不會報錯了。執行結果如下所示:

原文鏈接:https://blog.csdn.net/weixin_40228200/article/details/128624839

欄目分類
最近更新