1. //客户端:
Cpp代码
1. #include
2. #include
3. #include //一定要包含该头文件
4.
5. using namespace std;
6.
7. #pragma comment(lib, "WS2_32.lib") //windwows下的socket编程函数库
8.
9.
10. int main()
11. {
12. WSADATA wsaData;
13. WORD sockVersion = MAKEWORD(2, 2); //windows网络编程库的版本号信息
14. SOCKET sock = 0; //TCP通信的socket数据结构
15.
16. if (WSAStartup(sockVersion, &wsaData) != 0) //WSAStartup函数是在程序中初始化并加载Windows网络 //编程库的ws2_32.dll动态库文件。这个很重要。
17. {
18. cout << "initlization failed!" << endl;
19. exit(0); //如果WSAStartup返回值为1的话就表示ws2_32.dll文件有问题,程序退出
20. }
21.
22. sock = ::socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); //在本机上创建一个socket
23.
24. if (sock == INVALID_SOCKET) //判断socket是否创建成功
25. {
26. cout << "failed socket!" << endl;
27.
28. return 0; //如果创建失败就在程序中返回0结束程序
29. }
30.
31. sockaddr_in sin; //创建一个socket编程类型的网络地址数据结构以便connect函数对本机创建的socket数据 //结构进行初始化。
32.
33. sin.sin_family = AF_INET; //设置网络协议族类型
34. sin.sin_port = htons(4567); //设置远程计算机的端口号
35. sin.sin_addr.S_un.S_addr = inet_addr("127.0.0.1");//设置远程计算机的IP地址
36.
37. if (connect(sock, (sockaddr*)&sin, sizeof(sockaddr)) == -1) //初始化socket并连接远程计算机
38. {
39. cout << "connect failed!" << endl;
40.
41. return 0; //连接失败就返回0到程序
42. }
43.
44. char buffer[256] = "\0"; //声明一个从网络接收数据的缓存区
45. int nRecv = 0; //声明一个从网络接收到的数据字节长度
46.
47. nRecv = recv(sock, buffer, 256, 0); //recv是一个接收网络的TCP数据包函数,nRecv是从网络接收到数 //据的字节长度
48.
49. if (nRecv > 0)
50. {
51. buffer[nRecv] = '\0'; //如果接收到网络数据包长度大于0的话就在接收到的数据包未尾添加一个字符串 //结束符
52.
53. cout << "reveive data: " << buffer << endl;//按字符串格式输出接收到的数据
54. }
55.
56. closesocket(sock); //关闭这个TCP网络通信连接
57.
58. WSACleanup(); //释放ws2_32.dll动态库
59. }
1. //服务端:
Cpp代码
1. #include
2. #include
3. #include //一定要包含该头文件
4.
5. using namespace std;
6.
7. #pragma comment(lib, "WS2_32.lib") //windwows下的socket编程函数库 8.
9.
10. int main()
11. {
12. WSADATA wsaData;
13. WORD sockVersion = MAKEWORD(2, 2); //windows网络编程库的版本号信息
14. SOCKET sListen = 0; //TCP通信的socket数据结构 15. sockaddr_in sin = {0}; //创建一个socket编程类型的网络地址数据结构这个用于本地 16. sockaddr_in remoteAddr = {0};//创建一个socket编程类型的网络地址数据结构这个用于储存远程主机的 //IP地址和端口号
17. char szText[] = "TCP Server Demo";
18. int nAddrLen = 0;
19.
20. nAddrLen = sizeof(sockaddr_in); //计算这个sockaddr_in数据结构的大小
21. //fill sin
22. sin.sin_port = htons(4567); //设置本地(这里指服务端)计算机要打开的端口
23. sin.sin_family = AF_INET; //设置网络通信的网络协议族类型 24. sin.sin_addr.S_un.S_addr = INADDR_ANY; //设置本地计算机的IP地址,一般INADDR_ANY在程序运行时 //会自动计算成本地的IP地址的
25.
26. //init wsa
27. if (WSAStartup(sockVersion, &wsaData) != 0)//WSAStartup函数是在程序中初始化并加载Windows网络 //编程库的ws2_32.dll动态库文件。这个很重要。 28. {
29. cout << "initlization failed!" << endl;
30.
31. exit(0); //如果WSAStartup返回值为1的话就表示ws2_32.dll文件有问题,程序退出 32. }
33.
34. sListen = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); //在本机上创建一个socket
35. //使用bind函数绑定本机的ip和打开端口到本机创建的socket结构上,并初始化该socket //重点说明一个在服务器上是用bind函数来初始化socket,在客户机上是用connect函数来初始化socket的喔 36. if (bind(sListen, (LPSOCKADDR)&sin, sizeof(sin)) == SOCKET_ERROR)
37. {
38. cout << "bind failed!" << endl;
39.
40. return 0; //如果socket绑定失败返回程序0并退出程序
41. }
42.
43. if (listen(sListen, 2) == SOCKET_ERROR) //listen是用来打开本地计算机的端口,参数2表示客户端同 //时连接服务器的数量,这里是说可以同时有2个客户端连接 //到本机打开的端口
44. {
45. cout << "listen failed!" << endl;
46.
47. return 0; //如果打开本地端口失败就返回0并退出程序
48. }
49.
50. SOCKET sClient = INADDR_ANY; //再服务器上再创建一个socket结构,用来储存与一个客户端进行通信连 //接的连接实例
51.
52. while (true)
53. { //accept函数是用来创建一个TCP通信连接实例的,他使用一个远程计算机的IP地址和本地计算机上创建的一个 //socket,这两个信息来创建一个本地计算机到远程计算机的一个TCP通信连接实例的socket,sClient就是当前 //程序中的这个连接实例的socket 了。注accept函数也可以直接理解为接受一个客户机的连接请求。 54. sClient = accept(sListen, (SOCKADDR*)&remoteAddr, &nAddrLen);
55.
56. if (sClient == INVALID_SOCKET)
57. {
58. cout << "accept failed!" << endl;
59.
60. continue; //如果本地计算机(服务器)接受一个客户端连接请求失败就退出监听状态
61. }
62. //send函数是在TCP连接建立之后,就来发送数据的。其中sClient是存放有一个连接实例的socket结构来 //的。这个服务器上的send函数的socket参数和客户机上的socket参数是不同的喔,记住这里的socket参数是通过 //accept函数创建的喔。不是用connet函数和bind函数创建喔。 一定要记住这个sClient是一个关键来的。然后 //szText就是我们想要发送的数据了。这里我们向连接到该服务器的客户端发送了一个“TCP Server Demo”的信息。 63. send(sClient, szText, strlen(szText), 0);
64.
65. closesocket(sClient); //关闭这个用accept函数建立socket对象,关闭与remoteAddr连接通信。 //remoteAddr这结构理包含了有远程计算机的IP和端口号信息,当客户机 //使用connect函数发送一个连接请求时,被accept函数接受并处理后,远 //程计算机的IP地址和端口信息就被填到了remoteAddr这个结构中去 //了。
66.
67. }
68.
69. closesocket(sListen); //关闭本地计算机(服务器)上的由bind函数创建的socket对象,关闭本机 //打开的端口,关闭服务器
70.
71. WSACleanup(); //释放ws2_32.dll动态库 72. }
|