[推薦]windows網路編程經典入門

來源:互聯網
上載者:User
[推薦]windows網路編程經典入門
caiyi9000 原作

對於一個windows網路編程初學者,下面方法是經典入門。
初學者建議不要用MFC提供的類,而用windows API做一個簡單伺服器和用戶端,這樣有助於對socket編程機制的理解。
為了簡單起見,應用程式是基於MFC的標準對話方塊。
Winsock用WINDOWS API實現:
(1)伺服器端有兩個線程:
主線程 — 你需要編寫以下函數來實現

#define NETWORK_EVENT USER_MESSAGE+100 file://定義網路事件
sockaddr_in clientaddr; file://暫時存放用戶端IP地址

file://自己定義訊息映射函數,將上面定義的網路事件映射到處理函數
file://OnNetEvent為網路事件處理函數,它在下面定義
ON_MESSAGE(NETWORK_EVENT, OnNetEvent);

在你對話方塊中的初始化函數中調用下面的初始化網路的子函數
BOOL InitNetwork() file://初始化網路
{
file://初始化TCP協議
BOOL ret = WSAStartup(MAKEWORD(2,2), &wsaData);
if(ret != 0)
{
MessageBox("初始化通訊端失敗!");
return FALSE;
}

file://建立伺服器端通訊端
SOCKET serverSocket
= socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if(serverSocket == INVALID_SOCKET)
{
MessageBox("建立通訊端失敗!");
closesocket(m_Socket);
WSACleanup();
return FALSE;
}

file://綁定到本地一個連接埠上
sockaddr_in localaddr;
localaddr.sin_family = AF_INET;
localaddr.sin_port = htons(1688);
localaddr.sin_addr.s_addr = 0;
if(bind(serverSocket ,(const struct sockaddr*)&localaddr,
sizeof(sockaddr)) == SOCKET_ERROR)
{
MessageBox("綁定地址失敗!");
closesocket(m_Socket);
WSACleanup();
return FALSE;
}

file://註冊網路非同步事件,m_hWnd為應用程式的主對話方塊或主視窗的控制代碼
WSAAsyncSelect(serverSocket, m_hWnd, NETWORK_EVENT,
FD_ACCEPT | FD_CLOSE | FD_READ | FD_WRITE);

listen(serverSocket, 5); file://設定偵聽模式

return TRUE;
}

file://定義網路事件的響應函數
void OnNetEvent(WPARAM wParam, LPARAM lParam)
{
file://調用API函數,得到網路事件類型
int iEvent = WSAGETSELECTEVENT(lParam);

file://得到發出此事件的用戶端通訊端
SOCKET pSock = (SOCKET)wParam;

switch(iEvent)
{
case FD_ACCEPT: file://用戶端串連請求
{
OnAccept();

break;
}
case FD_CLOSE: file://用戶端斷開事件:
{
OnClose(pSock);
break;
}
case FD_READ: file://網路資料包到達事件
{
OnReceive(pSock);
break;
}
case FD_WRITE: file://發送網路資料事件
{
OnSend(pSock);
break;
}
default: break;
}
}

void OnAccept(SOCET pSock) file://響應用戶端串連請求函數
{
int len = sizeof(sockaddr);

file://調用API函數,接受串連,並返回一個新通訊端
file://還可以獲得用戶端的IP地址
SOCKET clientSocket = accept(serverSocket,
(struct sockaddr*)&clientaddr, &len);

file://為新的socket註冊非同步事件,注意沒有Accept事件
if(WSAAsyncSelect(clientSocket ,m_hWnd, IP_EVENT,
FD_CLOSE | FD_READ | FD_WRITE) == SOCKET_ERROR)
{
MessageBox("註冊非同步事件失敗!");
return;
}

file://自編函數,將此用戶端的相關資訊儲存下來:通訊端、
// IP地址、登陸時間
saveClientSocket(clientSocket,clientAddr,currentTimer);
}

void OnClose(SOCET pSock)
{
file://自編函數,結束與相應的用戶端的通訊,釋放相應資源並做相應處理
endClientSocket(pSock);
}

void OnSend(SOCET pSock)
{
file://自編函數,在給用戶端發資料時做一些預先處理
handleOnSend(pSock);
}

void OnReceive(SOCET pSock)
{
recv(...); file://調用API函數,讀出網路緩衝區中的資料包

file://自編函數,將此資料包和發出此資料的用戶端
file://clientSocket封裝成一條網路訊息
buildNetMsg(...);

file://自編函數,將此網路訊息放入一個訊息佇列中,由背景工作執行緒去處理
saveNetMsg(...);
SetEvent(...); file://用事件對象觸發背景工作執行緒
}

用戶端登陸後,隨即把自己的電腦名稱發給伺服器,伺服器接到後,把它儲存下來。這樣伺服器就可以顯示所有線上用戶端的資訊了,包括:用戶端電腦名、IP地址、登陸時間等。

注意: 用戶端沒有OnAccept()函數,但有OnConnect()函數。

背景工作執行緒 —
在你的應用程式初始化時,建立並啟動一個背景工作執行緒

AfxBeginThread(WorkThread,this,THREAD_PRIORITY_NORMAL);
file://this可能為應用程式的主對話方塊或主視窗的控制代碼

UINT WorkThread(LPVOID pParam)
{
while(1)
{
file://等待多重事件到來
int ret = WaitForMultipleObject(...);

switch(ret)
{
case OBJECT_0:
{
if(bNewNetMsg) file://查看網路訊息佇列是否有新的網路訊息
{
readNetMsg(...); file://如有新的網路訊息,則讀出
handleNetMsg(...); file://處理此網路訊息
}
break;
}
case OBJECT_0 + 1:
{
file://做退出處理
break;
}
default: break;
}

return 0;
}

用戶端為單線程,登陸伺服器時,用connect()函數給伺服器發串連請求;
用戶端沒有OnAccept()函數,但有OnConnect()函數。
在OnConnect()函數裡做發串連請求時的預先處理;
在OnReceive()函數裡響應並處理網路資料;
在OnClose()函數裡響應伺服器的關閉事件;
在OnSend()函數裡做發資料時的預先處理;

如果你還想實現各用戶端之間的線上交流(即所謂的聊天室),你在用戶端還可以基於UDP協議
再做一套多點對多點的區域網路組播模型模型,以後在和你聊,你先把上面的程式實現。

以上的I/O非同步模型基於Windows的訊息機制,另外還可以用事件模型、重疊模型或完成連接埠模型,
建議你參考Windows網路編程指南之類的書。

如果你能對上面的機制很熟練,你肯定已經對Winsock編網路程式的機制有一定理解,接下來你可以進行更精彩的編程, 不僅可以在網上傳輸普通資料,而且還
以傳輸語音、視頻資料,你還可以自己做一個聊天室,和你的同學在實驗室的區域網路裡可以共同分享你的成果。

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.