91超碰碰碰碰久久久久久综合_超碰av人澡人澡人澡人澡人掠_国产黄大片在线观看画质优化_txt小说免费全本

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

C++多線程實現TCP服務器端同時和多個客戶端通信

發布時間:2021-05-17 11:24:58 來源:億速云 閱讀:1024 作者:小新 欄目:開發技術

這篇文章主要介紹了C++多線程實現TCP服務器端同時和多個客戶端通信,具有一定借鑒價值,感興趣的朋友可以參考下,希望大家閱讀完這篇文章之后大有收獲,下面讓小編帶著大家一起了解一下。

通訊建立后首先由服務器端發送消息,客戶端接收消息;接著客戶端發送消息,服務器端接收消息,實現交互發送消息。

服務器同時可以和多個客戶端建立連接,進行交互;

在某次交互中,服務器端或某客戶端有一方發送"end"即終止服務器與其的通信;服務器還可以繼續接收其他客戶端的請求,與其他客戶端通信。

服務器端

#include <WinSock2.h>
#include <WS2tcpip.h>
#include <iostream>
using namespace std;
#pragma comment(lib, "ws2_32.lib")
#define PORT 65432
DWORD WINAPI ThreadFun(LPVOID lpThreadParameter);
int main() 
{
	//初始化winsock2.DLL
	WSADATA wsaData;
	WORD wVersionRequested = MAKEWORD(2, 2);
	if (WSAStartup(wVersionRequested, &wsaData) != 0)
	{
		cout << "加載winsock.dll失敗!" << endl;
		return 0;
	}
	//創建套接字
	SOCKET  sock_server;
	if ((sock_server = socket(AF_INET, SOCK_STREAM, 0)) == SOCKET_ERROR)
	{
		cout << "創建套接字失敗!錯誤代碼:" << WSAGetLastError() << endl;
		WSACleanup();
		return 0;
	}
	//綁定端口和Ip
	sockaddr_in addr;
	addr.sin_family = AF_INET;
	addr.sin_port = htons(PORT);
	inet_pton(AF_INET, "127.0.0.1", &addr.sin_addr);//綁定本機的環回地址
	if (SOCKET_ERROR == bind(sock_server, (SOCKADDR*)&addr, sizeof(sockaddr_in)))
	{
		cout << "地址綁定失敗!錯誤代碼:" << WSAGetLastError() << endl;
		closesocket(sock_server);
		WSACleanup();
		return 0;
	}
	//將套接字設為監聽狀態
	listen(sock_server, 0);
	
	//主線程循環接收客戶端的連接
	while (1) 
	{
		sockaddr_in addrClient;
		int len = sizeof(sockaddr_in);
		//接收成功返回與client通訊的socket
		SOCKET con = accept(sock_server, (SOCKADDR*)&addrClient, &len);
		if (con != INVALID_SOCKET) 
		{
			//創建線程 并且傳入與client通訊的套接字
			HANDLE hThread = CreateThread(NULL, 0, ThreadFun, (LPVOID)con, 0, NULL);
			CloseHandle(hThread); //關閉對線程的引用
		}
	}
	closesocket(sock_server);
	WSACleanup();
	return 0;
}
//線程通訊部分
DWORD WINAPI ThreadFun(LPVOID lpThreadParameter) 
{
	//與客戶端通訊 先發送再接收數據
	SOCKET sock = (SOCKET)lpThreadParameter;
	cout << "成功和" << sock << "建立連接!" << endl;
	while (1)
	{
		char msgbuffer[1000];//字符緩沖區
		printf("服務器向%d發送數據:\n", sock);
		cin.getline(msgbuffer, sizeof(msgbuffer));
		int size = send(sock, msgbuffer, sizeof(msgbuffer), 0);//給客戶端發送一段信息
		if (strcmp(msgbuffer, "end\0") == 0)
		{
			cout << "關閉和" << sock << "的連接!" << endl;
			return 0;
		}
		if (size == SOCKET_ERROR || size == 0)
		{
			cout << "發送信息失敗!錯誤代碼:" << WSAGetLastError() << endl;
			return 0;
		}
		else cout << "信息發送成功!" << endl;
		
		//接收客戶端數據
		msgbuffer[999] = { 0 };
		int ret = recv(sock, msgbuffer, sizeof(msgbuffer), 0);
		if(ret == SOCKET_ERROR || ret == 0)
		{
			cout << sock << "斷開了連接!" << endl;
			break;
		}
		else cout << sock << "  說: " << msgbuffer << endl;
	}
	return 0;
}

客戶端

#include <winsock2.h>
#include <WS2tcpip.h>
#include <iostream>
using  namespace std;
#pragma comment(lib, "ws2_32.lib")
#define PORT 65432
int  main() 
{
	//初始化winsock2.DLL
	WSADATA wsaData;
	WORD wVersionRequested = MAKEWORD(2, 2);
	if (WSAStartup(wVersionRequested, &wsaData) != 0)
	{
		cout << "加載winsock.dll失敗!" << endl;
		return 0;
	}
	//創建套接字
	SOCKET  sock_client; 
	if ((sock_client = socket(AF_INET, SOCK_STREAM, 0)) == SOCKET_ERROR)
	{
		cout << "創建套接字失敗!錯誤代碼:" << WSAGetLastError() << endl;
		WSACleanup();
		return 0;
	}
	//連接服務器
	sockaddr_in   addr;
	addr.sin_family = AF_INET;
	addr.sin_port = htons(PORT);
	inet_pton(AF_INET, "127.0.0.1", &addr.sin_addr);//綁定本機的環回地址
	int len = sizeof(sockaddr_in);
	if (connect(sock_client, (SOCKADDR*)&addr, len) == SOCKET_ERROR) {
		cout << "連接失敗!錯誤代碼:" << WSAGetLastError() << endl;
		return 0;
	}
	//實現交互部分,客戶端先接收后發送數據
	while (1)
	{
		//接收服務端的消息
		char msgbuffer[1000] = { 0 };
		int size = recv(sock_client, msgbuffer, sizeof(msgbuffer), 0);
		if (strcmp(msgbuffer, "end\0") == 0)
		{
			cout << "服務器端已經關閉連接!" << endl;
			break;
		}
		if (size < 0)
		{
			cout << "接收信息失敗!錯誤代碼:" << WSAGetLastError() << endl;
			break;
		}
		else if (size == 0)
		{
			cout << "對方已經關閉連接" << endl;
			break;
		}
		else cout << "The message from Server:" << msgbuffer << endl;

		//從鍵盤輸入一行文字發送給服務器
		msgbuffer[999] =  0 ;
		cout << "從鍵盤輸入發給服務器的信息:" << endl;
		cin.getline(msgbuffer, sizeof(msgbuffer));
		if (strcmp(msgbuffer, "end\0") == 0)
		{
			cout << "關閉連接!" << endl;
			break;
		}
		int ret = send(sock_client, msgbuffer, sizeof(msgbuffer), 0);
		if (ret == SOCKET_ERROR || ret == 0)
		{
			cout << "發送信息失敗!錯誤代碼:" << WSAGetLastError() << endl;
			break;
		}
		else cout << "信息發送成功!" << endl;
	}
	closesocket(sock_client);
	WSACleanup();
	return 0;
}

我們用建立連接時服務器端接收的客戶端套接字來唯一標識該客戶端。
服務器端可以隨時接收客戶端的連接并與其進行交互。

運行實例

C++多線程實現TCP服務器端同時和多個客戶端通信

實例展示了服務器端和兩個客戶端通信的運行過程,包括正常交互、交互過程中另一服務器請求建立連接、服務器主動斷開連接和客戶端主動斷開連接等過程。

感謝你能夠認真閱讀完這篇文章,希望小編分享的“C++多線程實現TCP服務器端同時和多個客戶端通信”這篇文章對大家有幫助,同時也希望大家多多支持億速云,關注億速云行業資訊頻道,更多相關知識等著你來學習!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

c++
AI

巨野县| 建始县| 文水县| 文化| 临猗县| 延吉市| 于都县| 土默特左旗| 巩留县| 邓州市| 彝良县| 图们市| 万盛区| 曲阳县| 泗水县| 岑溪市| 商南县| 丁青县| 团风县| 南岸区| 沙湾县| 临泽县| 洱源县| 正阳县| 南丹县| 耒阳市| 二连浩特市| 永吉县| 晋州市| 绿春县| 商城县| 嫩江县| 镇赉县| 轮台县| 尼玛县| 安阳县| 江阴市| 林周县| 武邑县| 电白县| 宣武区|