python 併發程式設計 協程 gevent模組

2022-09-16 05:06:15 字數 3619 閱讀 4279

單執行緒下,多個任務,io密集型程式

安裝

pip3 install gevent

gevent 是乙個第三方庫,可以輕鬆通過gevent實現併發同步或非同步程式設計,在gevent中用到的主要模式是greenlet, 它是以c擴充套件模組形式接入python的輕量級協程。 greenlet全部執行在主程式作業系統程序的內部,但它們被協作式地排程。

#

用法g1=gevent.spawn(func,1,2,3,x=4,y=5)

建立乙個協程物件g1,spawn括號內第乙個引數是函式名,如eat,後面可以有多個引數,可以是位置實參或關鍵字實參,都是傳給函式eat的

g2=gevent.spawn(func2)

g1.join()

#等待g1結束

g2.join()

#等待g2結束

#或者上述兩步合作一步:gevent.joinall([g1,g2])

g1.value

#拿到func1的返回值

遇到io立刻 切換到另外乙個任務,這是使用gevent.sleep 自己產生的io操作

import

gevent

import

time

defeat(name):

print("

%s:eat 1

" %name)

gevent.sleep(3)

print("

%s:eat 2

" %name)

defplay(name):

print("

%s:play 1

" %name)

gevent.sleep(4)

print("

%s:play 2

" %name)

g1 = gevent.spawn(eat,"

mike")

g2 = gevent.spawn(play,"

mike")

start_time =time.time()

g1.join()

g2.join()

end_time =time.time()

print(end_time-start_time)

'''mike:eat 1

mike:play 1

mike:eat 2

mike:play 2

4.0012290477752686

'''

而time.sleep(2)或其他的阻塞,gevent是不能直接識別的,遇到io不切換另外乙個任務

gevent模組 只能識別自己模擬的io操作,其他io操作無法識別

import

gevent

import

time

defeat(name):

print("

%s:eat 1

" %name)

time.sleep(3)

print("

%s:eat 2

" %name)

defplay(name):

print("

%s:play 1

" %name)

time.sleep(4)

print("

%s:play 2

" %name)

g1 = gevent.spawn(eat,"

mike")

g2 = gevent.spawn(play,"

mike")

start_time =time.time()

g1.join()

g2.join()

end_time =time.time()

print(end_time-start_time)

'''mike:eat 1

mike:eat 2

mike:play 1

mike:play 2

7.0004003047943115

'''

需要用下面一行**,打補丁,就可以識別了,

from gevent import monkey;monkey.patch_all()必須放到被打補丁者的前面,如time,socket模組之前

或者我們乾脆記憶成:要用gevent,需要將from gevent import monkey;monkey.patch_all()放到檔案的開頭

把monkey.pathch_all() 下面所有**的涉及到io阻塞操作都打個標記,變成非阻塞操作,讓gevent可以識別

這樣就可以檢測到io操作

from gevent import

monkey;monkey.patch_all()

import

gevent

import

time

defeat(name):

print("

%s:eat 1

" %name)

time.sleep(3)

print("

%s:eat 2

" %name)

defplay(name):

print("

%s:play 1

" %name)

time.sleep(4)

print("

%s:play 2

" %name)

g1 = gevent.spawn(eat,"

mike")

g2 = gevent.spawn(play,"

mike")

start_time =time.time()

g1.join()

g2.join()

end_time =time.time()

print(end_time-start_time)

'''mike:eat 1

mike:play 1

mike:eat 2

mike:play 2

4.032230854034424

'''

join()  主線程等待任務執行完後才銷毀

joinall()  等待多個任務 用列表存放任務

from gevent import

monkey;monkey.patch_all()

import

gevent

import

time

defeat(name):

print("

%s:eat 1

" %name)

time.sleep(3)

print("

%s:eat 2

" %name)

defplay(name):

print("

%s:play 1

" %name)

time.sleep(4)

print("

%s:play 2

" %name)

g1 = gevent.spawn(eat,"

mike")

g2 = gevent.spawn(play,"

mike")

gevent.joinall([g1,g2])

python 併發程式設計 協程 協程介紹

協程 是單執行緒下的併發,又稱微執行緒,纖程。英文名coroutine。一句話說明什麼是執行緒 協程是一種使用者態的輕量級執行緒,即協程是由使用者程式自己控制排程的 需要強調的是 1.python的執行緒屬於核心級別的,即由作業系統控制排程 如單執行緒遇到io或執行時間過長就會被迫交出cpu執行許可...

Python 併發程式設計(協程)

本章節主要介紹,使用單執行緒實現併發,即只用乙個主線程 很明顯可利用cpu只有乙個 為此我們需要先回顧下併發的本質 切換 儲存狀態 ps 在介紹程序理論時,提及程序的三種執行狀態,而執行緒才是執行單位,所以也可以將上圖理解為執行緒的三種狀態 單執行緒下併發稱為 協程 特點 缺點 gevent 是乙個...

併發程式設計 協程

一 協程介紹 協程 是單執行緒下的併發,又稱微執行緒,纖程。英文名coroutine。一句話說明什麼是執行緒 協程是一種使用者態的輕量級執行緒,即協程是由使用者程式自己控制排程的。需要強調的是 對比作業系統控制線程的切換,使用者在單執行緒內控制協程的切換 優點如下 缺點如下 總結 必須在只有乙個單執...