select poll epoll IO操作多路复用及猴子补丁
一:select(能監(jiān)控數(shù)量有限,不能告訴用戶程序具體那個連接有數(shù)據(jù))
select目前幾乎所有的平臺都支持,其良好的跨平臺支持也是一個優(yōu)點
select的缺點在于單個進程能夠監(jiān)控的文件描述的數(shù)量存在最大限制(在liunx上一般是1024)
select監(jiān)控socket連接是不能準確告訴用戶是哪個
二:poll(和select一樣,僅僅去除了最大監(jiān)控數(shù)量)
poll和select在本質(zhì)上沒有太大差別,但是poll沒有最大文件描述限制
三:epoll(不僅沒有最大監(jiān)控數(shù)量限制,還能告訴用戶哪個連接有活躍)
epoll沒有最大文件描述數(shù)量限制,還可以直接告訴用戶程序是哪一個
四. epoll能實現(xiàn)高并發(fā)原理
內(nèi)存映射(mmap):內(nèi)存映射文件,是由一個文件到一塊內(nèi)存的映射,將不必再對文件執(zhí)行I/O操作
五.epoll和select,poll還有一個本質(zhì)的區(qū)別的就是:
select 和 poll 只有在下次在循環(huán)回來,再去操作系統(tǒng)獲取文件描述符
epoll 會直接告訴程序,我們這里已經(jīng)就緒了,你可以接受數(shù)據(jù)了,等下一次協(xié)程去調(diào)用 epoll_wait 的時候就可以直接拿到就緒的文件描述符
IO操作
服務(wù)器端編程經(jīng)常需要構(gòu)造高性能的IO模型,常見的IO模型有四種:
- (1)同步阻塞IO(Blocking IO):即傳統(tǒng)的IO模型
- (2)同步非阻塞IO(Non-blocking IO):默認創(chuàng)建的socket都是阻塞的,非阻塞IO要求socket被設(shè)置為NONBLOCK。注意這里所說的NIO并非Java的NIO(New IO)庫
- (3)IO多路復用(IO Multiplexing):即經(jīng)典的Reactor設(shè)計模式,有時也稱為異步阻塞IO,Java中的Selector和Linux中的epoll都是這種模型
- (4)異步IO(Asynchronous IO):即經(jīng)典的Proactor設(shè)計模式,也稱為異步非阻塞IO
同步和異步的概念描述的是用戶線程與內(nèi)核的交互方式:
同步是指用戶線程發(fā)起IO請求后需要等待或者輪詢內(nèi)核IO操作完成后才能繼續(xù)執(zhí)行
異步是指用戶線程發(fā)起IO請求后仍繼續(xù)執(zhí)行,當內(nèi)核IO操作完成后會通知用戶線程,或者調(diào)用用戶線程注冊的回調(diào)函數(shù)。
阻塞和非阻塞的概念描述的是用戶線程調(diào)用內(nèi)核IO操作的方式:
阻塞是指IO操作需要徹底完成后才返回到用戶空間
非阻塞是指IO操作被調(diào)用后立即返回給用戶一個狀態(tài)值,無需等到IO操作徹底完成
I/O的實質(zhì)是什么?
I/O的實質(zhì)是將硬盤中的數(shù)據(jù),或收到的數(shù)據(jù)實現(xiàn)從內(nèi)核態(tài) copy到 用戶態(tài)的過程
用戶態(tài) & 內(nèi)核態(tài)
系統(tǒng)空間分為兩個部分,一部分是內(nèi)核態(tài),一部分是用戶態(tài)的部分
內(nèi)核態(tài):內(nèi)核態(tài)的空間資源只有操作系統(tǒng)能夠訪問
用戶態(tài):我們寫的普通程序使用的空間
IO多路復用
IO多路復用:
- I/O是指網(wǎng)絡(luò)I/O
- 多路指多個TCP連接(即socket或者channel)
- 復用指復用一個或幾個線程
- 意思說一個或一組線程處理多個TCP連接
- 最大優(yōu)勢是減少系統(tǒng)開銷,不必創(chuàng)建過多的進程/線程,也不必維護這些進程/線程
IO多路復用使用兩個系統(tǒng)調(diào)用(select/poll/epoll和recvfrom)
- blocking IO只調(diào)用了recvfrom
- select/poll/epoll 核心是可以同時處理多個connection(連接)
- 多路復用模型中,每一個socket,設(shè)置為non-blocking,阻塞是被select這個函數(shù)block,而不是被socket阻塞的
六.猴子補丁
即在運行時對方法 / 類 / 屬性 / 功能進行修改,把新的代碼作為解決方案代替原有的程序,也就是為其打上補丁。
在使用gevent模塊的使用會遇到猴子補丁import gevent.monkeygevent.monkey.patch_all()注解:使用猴子補丁的方式,gevent能夠修改標準庫里面大部分的阻塞式系統(tǒng)調(diào)用,包括socket、ssl、threading和 select等模塊,而變?yōu)閰f(xié)作式運行。也就是通過猴子補丁的monkey.patch_xxx()來將python標準庫中模塊或函數(shù)改成gevent中的響應的具有協(xié)程的協(xié)作式對象。這樣在不改變原有代碼的情況下,將應用的阻塞式方法,變成協(xié)程式的。
總結(jié)
以上是生活随笔為你收集整理的select poll epoll IO操作多路复用及猴子补丁的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 类的实例方法静态方法类方法属性方法属性
- 下一篇: python2和3的区别字符编码格式上下