多路復用i/o模型支援多client的實現及效率討論
發表日期:2004-04-28
在標頭檔案中包含了「winsock.h」和"#pragma comment(lib,"wsock32")"
1. 引言
多路復用i/o模型(select)是unix/linux用得的最多的一種i/o模型,在windows下也
可做為一種非同步i/o使用。本文給出該i/o模型處理多client的簡單(在主線程中)實現。
2. 關於select
select i/o模型是一種非同步i/o模型,在單執行緒中linux/winnt預設支援64個客戶端套
接字。這種i/o模型主要涉及以下幾個函式及巨集:
int select(…)、fd_zero、fd_set、fd_isset以及fd_setsize。
3. 用select開發乙個server
3.1 只支援單個client
// 相關初始化處理, 建立監聽套接字
listen(listensock, 5);
clientsock = accept(listensock, null, null);
for (; ;) }
其實winsock中的wsaeventselect模型是與之類似的。
3.2 在單執行緒中支援63個client
socket clientsockarray[fd_setsize – 1]; // fd_setsize is 64
// 相關初始化處理, 建立監聽套接字
listen(listensock, 5);
// 初始化套接字陣列
initsock(clientsockarray);
fd_zero(&readfds);
fd_set(listensock, &readfds);
for (; ;)
} // 逐個處理處於待決狀態的套接字
for (nindex = 0; nindex < fd_setsize - 1; nindex++)
// 將接受到的資料進行處理,此處只將其輸出
printf("%s/n", buff);
} }
// 初始化套接字集合
fd_zero(&readfds);
fd_set(listensock, &readfds);
// 將所有有效的套接字控制代碼加入到套接字控制代碼陣列中
for (nindex = 0; nindex < fd_setsize - 1; nindex++) }
bool insertsock(socket* psock, socket sock) }
if (nindex = = fd_setsize – 1)
return false;
return true;
} 上面只是給簡要的**,有的輔助函式也沒有給出。用select支援多client是比較方便的,在乙個執行緒中可支援63個;可以採用多執行緒支援更大數量的client。
4. 效率的討論
4.1 對套接字陣列掃瞄的效率問題
在上面的程式中,存在多處對套接字控制代碼的掃瞄處理,這個肯定會影響效率。不知道各位朋友是怎麼處理這個問題的。
4.2 對客戶端實時響應問題
上面的程式處理待決的套接字的時候,是逐個處理的,如果響應某個client的時間長到一定程度的話,肯定會影響對其它客戶端的響應。我的解決方法是當這個套接字處於可讀的待決狀態的話,產生乙個子執行緒去處理------接收資料和處理資料。這樣主線程繼續自己的工作,其它client可以得及時的響應;當然當有大量的client請求時,對執行緒的控制會成為乙個新問題。
IO模型 多路復用
乙個輸入操作通常包括兩個階段 應用程序被阻塞,直到資料從核心緩衝區複製到應用程序緩衝區中才返回。應該注意到,在阻塞的過程中,其它應用程序還可以執行,因此阻塞不意味著整個作業系統都被阻塞。因為其它應用程序還可以執行,所以不消耗 cpu 時間,這種模型的 cpu 利用率會比較高。應用程序執行系統呼叫之後...
IO模型 IO多路復用
用socket 一定會用到accept recv recvfrom這些方法 正常情況下 accept recv recvfrom都是阻塞的 如果setblocking false 整個程式就變成乙個非阻塞的程式了非阻塞的特點 沒有併發程式設計的機制 是乙個同步的程式 程式不會在某乙個連線的recv或...
IO模型 io多路復用(三)
兩者相互比較 1 如果只有乙個使用者連線server端,多路復用io還不如阻塞io效率高 2 相比阻塞io,多路復用io中間多了個反饋機制 3 多路復用io的 可以同時監控socket 多個socket物件coon1 coon2.recv 4 多路復用io可以識別有人連線某個coon3,然後告知有c...