乙個故事講清楚NIO

2022-07-03 11:54:11 字數 1841 閱讀 9667

乙個故事講清楚nio

假設某銀行只有10個職員。該銀行的業務流程分為以下4個步驟:

1) 顧客填申請表(5分鐘);

2) 職員審核(1分鐘);

3) 職員叫保安去金庫取錢(3分鐘);

4) 職員列印票據,並將錢和票據返回給顧客(1分鐘)。

我們看看銀行不同的工作方式對其工作效率到底有何影響。

每來乙個顧客,馬上由一位職員來接待處理,並且這個職員需要負責以上4個完整流程。當超過10個顧客時,剩餘的顧客需要排隊等候。

我們算算這個銀行乙個小時到底能處理多少顧客?乙個職員處理乙個顧客需要10分鐘(5+1+3+1)時間,乙個小時(60分鐘)能處理6個顧客,一共10個職員,那就是只能處理60個顧客。

可以看到銀行職員的工作狀態並不飽和,比如在第1步,其實是處於等待中。

這種工作其實就是bio,每次來乙個請求(顧客),就分配到執行緒池中由乙個執行緒(職員)處理,如果超出了執行緒池的最大上限(10個),就扔到佇列等待 。

如何提高銀行的吞吐量呢?

思路:分而治之,將任務拆分開來,由專門的人負責專門的任務。

具體來講,銀行專門指派一名職員a,a的工作就是每當有顧客到銀行,他就遞上**讓顧客填寫,每當有顧客填好表後,a就將其隨機指派給剩餘的9名職員完成後續步驟。

我們計算下這種工作方式下銀行乙個小時到底能處理多少顧客?

假設顧客非常多,職員a的工作處於飽和中,他不斷的將填好表的顧客帶到櫃檯處理,櫃檯乙個職員5分鐘能處理完乙個顧客,乙個小時9名職員能處理:9*(60/5)=108。

可見工作方式的轉變能帶來效率的極大提公升。

這種工作方式其實就nio的思路。下圖是非常經典的nio說明圖,mainreactor執行緒負責監聽server socket,accept新連線,並將建立的socket分派給subreactor;subreactor可以是乙個執行緒,也可以是執行緒池(一般可以設定為cpu核數),負責多路分離已連線的socket,讀寫網路資料,這裡的讀寫網路資料可模擬顧客填表這一耗時動作,對具體的業務處理功能,其扔給worker執行緒池完成。

可以看到典型nio有三類執行緒,分別是mainreactor執行緒、subreactor執行緒、wor**程。不同的執行緒幹專業的事情,最終每個執行緒都沒空著,系統的吞吐量自然就上去了。

第二種工作方式有沒有什麼可以提高的地方呢?

仔細檢視可發現第3步驟這3分鐘櫃檯職員是在等待中度過的,那怎麼能讓櫃檯職員保持滿負荷呢?

還是分而治之的思路,指派1個職員b來專門負責第3步驟。每當櫃檯員工完成第2步時,就通知職員b來負責與保安溝通取錢。這時候櫃檯員工可以繼續處理下乙個顧客。當職員b拿到錢之後,他會怎麼辦呢?他會通知顧客錢已經到櫃檯了,讓顧客重新排隊處理,當櫃檯職員再次服務該顧客時,發現該顧客前3步已經完成,直接執行第4步即可。

我們可以算算通過這種方法,銀行的吞吐量能提高到多少。

假設職員b的工作非常飽和,櫃檯乙個職員現在2分鐘能處理完乙個顧客,乙個小時8名職員能處理:8*(60/2)=240。

在當今web服務中,經常需要通過rpc或者http等方式呼叫第三方服務,這裡對應的就是第3步,如果這步耗時較長,通過非同步方式將能極大降低資源使用率。

jetty continuations 就實現了上述非同步方式,有興趣的同學可以去嘗試下(

nio+非同步的方式能讓少量的執行緒(資源)做大量的事情,這適用於很多應用場景,比如**服務、api服務、長連線服務等等,這些應用如果用同步方式將耗費大量機器資源。儘管nio+非同步能提高系統吞吐量,但其並不能讓乙個請求的等待時間下降,相反可能會增加等待時間。

總結就一句:「分而治之,將任務拆分開來,由專門的人負責專門的任務」,這不僅在計算機領域生效,在整個社會領域都生效。

一文講清楚事務隔離性

乙個人運算元據庫的時候,其他人都看不見 其他人不能讀 mvcc 其他人不能寫 通過加鎖 鎖 read view一般由兩部分組成 排他鎖小紅對取前的時候加上了鎖 排他鎖 所以其他人不能取錢了,所以等小紅這個操作 事務 結束了,這把鎖才能解開 事務的開始時間是更新操作執行的時候 讀未提交沒有mvcc的控...

一文講清楚vim的map對映

map主用自定義快捷鍵,如 map a b 把b對映為a鍵,使之按下a的時候執行b快捷鍵 在vim配置檔案中經常會看到map nmap imap vmap vnoremap nunmap nmapclear等,都是什麼意思呢?map前的n v nore un等表示下列含義 如 nmap s wqa ...

一句話講清楚GIL鎖

什麼是 全域性gil鎖 全域性指的是所有cpu,鎖指的每次是只有乙個cpu的執行緒可以執行io任務 銀行四個視窗 程序 四個隊伍的客戶在排隊辦理業務,python中的 全域性gil鎖 的意思是 一旦有乙個視窗在辦理客戶的業務,其他三個視窗必須停止辦理,直到這個視窗辦理完業務,其他視窗才有機會給客戶辦...