python非同步IO的發展歷程

2021-08-11 16:42:11 字數 3360 閱讀 8775

python中非同步io發展分為三個發展階段

1.使用yield和send

2.使用@asyncio.coroutine和yield from

3.使用async/await關鍵字

def fib(n):

res = [0]*n

index = 0

a = 0

b = 1

while index < n:

res[index] = b

a, b = b, a + b

index += 1

return res

for res in fib(20):

print(res)

這是一段輸出斐波那契數列的**,需要經過數次迭代。這種方式的缺點是執行這種迭代運算需要占用大量記憶體,而我們最終的目的如果只是想得到某乙個順序位上的數字,該方法就不太合適了。

def fib(n):

res = [0]*n

index = 0

a = 0

b = 1

while index < n:

yield b

a, b = b, a + b

index += 1

for res in fib(20):

print(res)

當我們使用yield 時,無須在函式內加入return,直接用for in,便可直接得到yield的值,即沒執行一次,就會再執行一次next(fib(20)) (相當於執行下一次吧)。

import random

import time

def fib(n):

index = 0

a = 0

b = 1

while index < n:

sleep_cnt = yield b

print('delay seconds'.format(sleep_cnt))

time.sleep(sleep_cnt)

a, b = b, a + b

index += 1

n = 20

sfib = fib(n)

res = next(sfib)

while true:

print(res)

try:

res = sfib.send(random.uniform(0, 0.5))

except stopiteration:

break

當我們想往執行緒中傳送資料時,可以用到send函式,此處使用time庫,虛擬一下io的延遲。

def fibagain(n):

print('i am copy from fib')

yield from fib(n)

print('copy end')

for res in fibagain(20):

print(res)

以上**承接上文,由此可見,yield from相當於重構之前的yield的**,重新來一次重新整理。

loop.close()以上是乙個連線**的乙個例子,我們使用yield掛起需要非同步io的**,在函式前加入@asyncio.coroutine關鍵字,再使用實現執行緒的併發。

async def smart_fib(n):

index = 0

a = 0

b = 1

while index < n:

sleep_secs = random.uniform(0, 0.2)

await asyncio.sleep(sleep_secs)

print('smart one think {} secs to get {}'.format(sleep_secs, b))

a, b = b, a + b

index += 1

async def stupid_fib(n):

index = 0

a = 0

b = 1

while index < n:

sleep_secs = random.uniform(0, 0.4)

await asyncio.sleep(sleep_secs)

print('stupid one think {} secs to get {}'.format(sleep_secs, b))

a, b = b, a + b

index += 1

if __name__ == '__main__':

loop = asyncio.get_event_loop()

tasks = [

smart_fib(10)),

stupid_fib(10))

] loop.run_until_complete(asyncio.wait(tasks))

print('all fib finished.')

loop.close()

理解了yield from之後,async/await關鍵字就很好理解了,其實就是對yield from的簡化。

Python學習 非同步IO

在io程式設計一節中,我們已經知道,cpu的速度遠遠快於磁碟 網路等io。在乙個執行緒中,cpu執行 的速度極快,然而,一旦遇到io操作,如讀寫檔案 傳送網路資料時 就需要等待io操作完成,才能繼續進行下一步操作。這種情況稱為同步io 在io操作的過程中,當前執行緒被掛起,而其他需要cpu執行的 就...

python之非同步IO

我們知道,cpu的速度遠遠快於磁碟 網路等io。在乙個執行緒中,cpu執行 的速度極快,然而,一旦遇到io操作,如讀寫檔案 傳送網路資料時,就需要等待io操作完成,才能繼續進行下一步操作。這種情況稱為同步io。在io操作的過程中,當前執行緒被掛起,而其他需要cpu執行的 就無法被當前執行緒執行了。因...

MySQL的發展歷程

mysql名字由來 其實mysql最初的出發點是用msql和他們自己的快速低階例程 isam 去連線 不管怎樣,在經過一些測試後,開發者得出結論 msql的速度或靈活性不足以滿足要求。這導致了為資料庫提供了新的sql介面,這樣,這個api被設計成允許為用於msql而寫的第三方 更容易移植到mysql...