一、基于TCP的套接字编程实现流程:
1. 服务器端流程简介:
(1)创建套接字(socket)
(2)将套接字绑定到一个本地地址和端口上(bind)
(3)将套接字设定为监听模式,准备接受客户端请求(listen)
(4)阻塞等待客户端请求到来。当请求到来后,接受连接请求,返回一个新的对应于此客户端连接的套接字sockClient(accept)
(5)用返回的套接字sockClient和客户端进行通信(send/recv);
(6)返回,等待另一个客户端请求(accept)
(7)关闭套接字(close)
2. 客户端流程简介:
(1) 创建套接字(socket)
(2) 向服务器发出连接请求(connect)
(3) 和服务器进行通信(send/recv)
(4) 关闭套接字(close)
二、基于TCP的C++套接字编程实例:
(1)Sever实现:
#include <Winsock2.h> #include <cstdio> #include <iostream> #pragma comment(lib,"ws2_32.lib") int main() { //1. 加载socket函数库 WSADATA wsaData; SOCKET sockServer; SOCKADDR_IN addrServer; SOCKET sockClient; SOCKADDR_IN addrClient; WSAStartup(MAKEWORD(2,2),&wsaData); //加载套接字库 //2. 创建套接字 addrServer.sin_addr.S_un.S_addr = htonl(INADDR_ANY); //INADDR_ANY表示任何IP,即允许所有的客户端连接到本地服务端 addrServer.sin_family = AF_INET; //设置为IP通信 addrServer.sin_port = htons(6000); //绑定端口6000 sockServer = socket(AF_INET,SOCK_STREAM,0); //创建流式套接字 std::cout<<"创建套接字成功"<<std::endl; //3. 将套接字绑定到 固定IP和固定端口 bind(sockServer, (SOCKADDR*)&addrServer, sizeof(SOCKADDR)); //进行端口和IP地址的绑定 std::cout<<"绑定套接字成功"<<std::endl; //4. 将套接字设置为监听模式,等待连接到来 listen(sockServer,5); //监听队列为5 std::cout<<"监听连接中......"<<std::endl; int len = sizeof(SOCKADDR); char sendBuf[100]; //发送至客户端的字符串 char recvBuf[100]; //接受客户端返回的字符串 //5. 阻塞服务端的进程,直到有客户端连接为止 sockClient = accept(sockServer, (SOCKADDR*)&addrClient, &len); //sockClinet为返回的新的客户端连接 std::cout<<"收到连接:"<<inet_ntoa(addrClient.sin_addr)<<std::endl; //6. 接收并打印客户端数据 int recvlen = 0; if((recvlen = recv(sockClient,recvBuf,100,0)) > 0) { std::cout<<recvBuf<<std::endl; } send(sockClient, "Receive the Client Data", 23, 0); //7. 关闭socket closesocket(sockClient); WSACleanup(); return 0; }
(2)Client实现:
#include <WinSock2.h> #include <stdio.h> #include <iostream> #include <cstring> #pragma comment(lib, “ws2_32.lib”) int main() { //1. 加载套接字 WSADATA wsaData; if(WSAStartup(MAKEWORD(2, 2), &wsaData) != 0) { printf(”Failed to load Winsock”); return; } //2. 创建套接字 SOCKADDR_IN addrSrv; addrSrv.sin_family = AF_INET; addrSrv.sin_port = htons(6000); //端口号6000 addrSrv.sin_addr.S_un.S_addr = inet_addr("127.0.0.1"); //访问的服务器IP SOCKET sockClient = socket(AF_INET, SOCK_STREAM, 0); //创建客户端套接字 //3. 向服务器发出连接请求 if(connect(sockClient, (struct sockaddr*)&addrSrv, sizeof(addrSrv)) == INVALID_SOCKET) { std::cout<<"Connect failed:"<<WSAGetLastError()<<std::endl; return; } //4.接收和发送数据 char recvbuff[1024]; memset(recvbuff, 0, sizeof(recvbuff)); recv(sockClient, recvbuff, sizeof(recvbuff), 0); std::string sendbuf = "hello, this is a Client…"; send(sockClient, sendbuf.c_str(), sendbuf.size(), 0); //5. 关闭套接字 closesocket(sockClient); WSACleanup(); return 0; }