1. 程式人生 > >多路復用IO模型 IO multiplexing

多路復用IO模型 IO multiplexing

style 127.0.0.1 請求 int data 正常 並發 mage 分享圖片

多路復用IO模型

就非阻塞IO模型來說,雖然使得CPU處於高並發,但是絕大部分的計算機資源被用反復檢測。這樣對於少量的用戶絕對實在浪費資源。

這是提出多路復用IO模型

技術分享圖片

多路復用IO模型的結局方案,其實用select模塊作為一個檢測是否有想要的數據生成,如果沒有就去執行其他任務,如果有的話,之前原IO操作。將原來數個accept和recv等這種兩個io操作的阻塞變成了select模塊。

import select
import socket

server = socket.socket()
server.setsockopt(socket.SOL_SOCKET,socket.SO_REUSEADDR,
1) server.bind(("127.0.0.1",5555)) server.listen(5) server.setblocking(False) #需要檢測的是否可以別讀取的列表(accept,recv等操作) rlist = [server,]#服務端需要一直被檢測是否有客戶端,連接 #需要檢測的是否可以寫入的列表,(send操作) wlist = [] #需要發送的數據,目前是因為我們要把接受的數據在發送回去 dic = {} while True: rl,wl,xl = select.select(rlist,wlist,[]) for c in rl:
#當檢測當rlist中有可以讀取的操作(即可以連接對象) if c == server: #接受到客戶端的連接請求(一個讀操作) conn,addr = c.accept() #創建的連接添加加入檢測列表中去 rlist.append(conn) else: #不是服務就是客戶端的連接,就可以執行recv try: data = c.recv(1024) if
not data:#linux的客戶端的錯誤關閉的 c.close() rlist.remove(c)#將給連接從被檢測列表中移除 wlist.append(c)#在正常開發中,不可能必須客戶端先發送數據 #服務端才給客戶端發送請求 dic[c] = data except ConnectionResetError: c.close() rlist.remove(c) #處理可以寫的socket for c in wl: print(c) try: c.send(dic[c].upper()) dic.pop(c) #從檢測列表中刪除已發送完成的客戶端 wlist.remove(c) except BlockingIOError: pass

異步IO簡單的提一下

模型

技術分享圖片

其實上節課講的異步回調就是解決異步的方案,後期會將asyncio模塊。

多路復用IO模型 IO multiplexing