INADDR_ANY就是inet_addr("0.0.0.0")

首先,需要明确的是当服务器的监听地址是INADDR_ANY时设置的是服务器的IP地址。

   其次,当服务器的监听地址是INADDR_ANY时含义是让服务器端计算机上的所有网卡的IP地址都可以作为服务器IP地址,也即监听外部客户端程序发送到服务器端所有网卡的网络请求。

    比如,我的网络为:192.168.1.102. 于是就有下面的程序:

服务端:

#include <stdio.h>
#include <winsock2.h> // winsock接口
#pragma comment(lib, "ws2_32.lib") // winsock实现int main()
{WORD wVersionRequested;  // 双字节,winsock库的版本WSADATA wsaData;         // winsock库版本的相关信息
    wVersionRequested = MAKEWORD(1, 1); // 0x0101 即:257// 加载winsock库并确定winsock版本,系统会把数据填入wsaData中WSAStartup( wVersionRequested, &wsaData );// AF_INET 表示采用TCP/IP协议族// SOCK_STREAM 表示采用TCP协议// 0是通常的默认情况unsigned int sockSrv = socket(AF_INET, SOCK_STREAM, 0);SOCKADDR_IN addrSrv;addrSrv.sin_family = AF_INET; // TCP/IP协议族addrSrv.sin_addr.S_un.S_addr = INADDR_ANY; //inet_addr("0.0.0.0"); addrSrv.sin_port = htons(8888); // socket对应的端口// 将socket绑定到某个IP和端口(IP标识主机,端口标识通信进程)bind(sockSrv,(SOCKADDR*)&addrSrv, sizeof(SOCKADDR));// 将socket设置为监听模式,5表示等待连接队列的最大长度listen(sockSrv, 5);SOCKADDR_IN addrClient;int len = sizeof(SOCKADDR);while(1){// sockSrv为监听状态下的socket// &addrClient是缓冲区地址,保存了客户端的IP和端口等信息// len是包含地址信息的长度// 如果客户端没有启动,那么程序一直停留在该函数处unsigned int sockConn = accept(sockSrv,(SOCKADDR*)&addrClient, &len);char sendBuf[100] = {0};sprintf(sendBuf,"%s", inet_ntoa(addrClient.sin_addr)); // 将客户端的IP地址保存下来send(sockConn, sendBuf, strlen(sendBuf) + 1, 0); // 发送数据到客户端,最后一个参数一般设置为0char recvBuf[100] = {0};recv(sockConn, recvBuf, 100, 0); // 接收客户端数据,最后一个参数一般设置为0printf("%s\n", recvBuf);closesocket(sockConn);}closesocket(sockSrv);WSACleanup();return 0;
}

客户端:

#include <winsock2.h>
#include <stdio.h>
#pragma comment(lib, "ws2_32.lib")int main()
{WORD wVersionRequested;WSADATA wsaData;wVersionRequested = MAKEWORD(1, 1);WSAStartup( wVersionRequested, &wsaData );SOCKET sockClient = socket(AF_INET, SOCK_STREAM, 0);SOCKADDR_IN addrSrv;addrSrv.sin_addr.S_un.S_addr = inet_addr("192.168.1.102");addrSrv.sin_family = AF_INET;addrSrv.sin_port = htons(8888);int ret = connect(sockClient, (SOCKADDR*)&addrSrv, sizeof(SOCKADDR));char recvBuf[100] = {0};recv(sockClient, recvBuf, 100, 0);printf("%s\n", recvBuf);send(sockClient, "hello world", strlen("hello world") + 1, 0);closesocket(sockClient);WSACleanup();return 0;
}

当然客户端也可以用回测地址(设服务端与客户端在同一台机子上):

#include <winsock2.h>
#include <stdio.h>
#pragma comment(lib, "ws2_32.lib")int main()
{WORD wVersionRequested;WSADATA wsaData;wVersionRequested = MAKEWORD(1, 1);WSAStartup( wVersionRequested, &wsaData );SOCKET sockClient = socket(AF_INET, SOCK_STREAM, 0);SOCKADDR_IN addrSrv;addrSrv.sin_addr.S_un.S_addr = inet_addr("127.0.0.1");addrSrv.sin_family = AF_INET;addrSrv.sin_port = htons(8888);int ret = connect(sockClient, (SOCKADDR*)&addrSrv, sizeof(SOCKADDR));char recvBuf[100] = {0};recv(sockClient, recvBuf, 100, 0);printf("%s\n", recvBuf);send(sockClient, "hello world", strlen("hello world") + 1, 0);closesocket(sockClient);WSACleanup();return 0;
}

  当然啦,如果服务端用192.168.1.102作为监听IP,客户端用192.168.1.102去connect,  那也是可以的。

"将sin_addr设置为INADDR_ANY"的含义是什么?

问:

  很多书上都说“将sin_addr设置为INADDR_ANY,则表示所有的IP地址,也即所有的计算机”,这样的解说让人费解。

答:

  INADDR_ANY转换过来就是0.0.0.0,泛指本机的意思,也就是表示本机的所有IP,因为有些机子不止一块网卡,多网卡的情况下,这个就表示所有网卡ip地址的意思。

  当服务器的监听地址是INADDR_ANY时,意思不是监听所有的客户端IP。而是服务器端的IP地址可以随意配置,这样使得该服务器端程序可以运行在任意计算机上,可使任意计算机作为服务器,便于程序移植。将INADDR_ANY换成127.0.0.1也可以达到同样的目的。这样,当作为服务器的计算机的IP有变动或者网卡数量有增减,服务器端程序都能够正常监听来自客户端的请求。我是这么理解的。

  比如一台电脑有3块网卡,分别连接三个网络,那么这台电脑就有3个ip地址了,如果某个应用程序需要监听某个端口,那他要监听哪个网卡地址的端口呢?如果绑定某个具体的ip地址,你只能监听你所设置的ip地址所在的网卡的端口,其它两块网卡无法监听端口,如果我需要三个网卡都监听,那就需要绑定3个ip,也就等于需要管理3个套接字进行数据交换,这样岂不是很繁琐?所以出现INADDR_ANY,你只需绑定INADDR_ANY,管理一个套接字就行,不管数据是从哪个网卡过来的,只要是绑定的端口号过来的数据,都可以接收到。

INADDR_ANY的确切含义相关推荐

  1. 关于信噪比的确切含义——Eb/No和SNR的区别

    SNR:信号功率与噪声功率之比,这在模拟通信时,很合适做度量指标,但在数字通信中就不太合适 Eb/No:Eb(焦耳/比特),No(瓦特/赫兹),适合用作数字通信衡量系统性能的指标 SNR和Eb/No: ...

  2. 40隐式构造函数和隐式转换,还有explicit关键词的确切含义【C++学习笔记】

    40隐式构造函数和隐式转换,还有explicit关键词的确切含义 隐式的意思是:不会明确地告诉你它要做什么,它有点像在某种情况下自动的工作 隐式转换 double a = 0.5; int b = a ...

  3. git中“我们的”和“他们的”的确切含义是什么?

    本文翻译自:What is the precise meaning of "ours" and "theirs" in git? This might soun ...

  4. java什么叫实例化_在JAVA中实例化的确切含义是什么

    小编典典 首先 声明的意思是 : ClassName obj; 实例化的 简单含义 是从class创建一个对象 . ClassName obj = new ClassName(); 什么是物体? 类的 ...

  5. SCII控制字确切含义

    SCII控制字 十进制 代码 含义 00 NUL 空 01 SOH 标题开始 02 STX 正文开始 03 ETX 正文结束 04 EOT 传输结否 05 ENQ 询问 06 ACK 确认 07 BE ...

  6. [乐意黎]合同条款里的包括但不限于的确切含义

    "包括但不限于"是关于范围的概念,也是我们草拟法律专业文本时最常用也最喜欢用的一个词."包括但不限于"后面的内容是例举的部分内容,也就是被包括的一部分:还有一部 ...

  7. 上下文切换的确切含义了解下

    上下文切换的含义 其实在单个处理器的时期,操作系统就能处理多线程并发任务.处理器给每个线程分配 CPU 时间片(Time Slice),线程在分配获得的时间片内执行任务. CPU 时间片是 CPU 分 ...

  8. AutoEventWireup属性的确切含义

    使用Asp.NET时,新建的aspx页面第一行page指令中包含了一个AutoEventWireup属性.网上的很多教程认为这一属性,甚至这一行代码都是没用的.其实,这是不了解Asp.NET事件处理模 ...

  9. linux c socket programming

    http://54min.com/post/http-client-examples-using-c.html 好文章 PPT http://www.slideshare.net/Arbow/asyn ...

  10. C socket编程

    -------------------------------------------------------------------------------- 平台和编译器  这篇文档中的大多数代码 ...

最新文章

  1. EMC Networker与mhvtl虚拟磁带库的结合on rhel5.5
  2. python的控件text的文本属性_只需6行Python代码就给图片加上水印——你一看就会了...
  3. Sublime Text 2
  4. Chapter 1 First Sight——12
  5. java中获取文件总行数_关于java:如何以有效的方式获取文件中的行数?
  6. 个人代码库の自定义后缀名
  7. .NET遗留应用改造——性能优化篇
  8. Xamarin支持微软HoloLens混合现实开发
  9. C# 用委托实现Callback
  10. Java中使用poi导入、导出Excel
  11. HCIE-Security Day21:GRE协议:实验(二)配置基于OSPF的GRE隧道
  12. 一文详解Matlab中Psychtoolbox工具箱的安装方法
  13. python怎么画波浪,字符波浪|Python练习系列[14]
  14. 春秋旅游移动app设计界面
  15. 千克与磅之间的转换 Exercise05_05
  16. 如何拥有一颗平常心?(KK记)
  17. Word中灵活的首字下沉
  18. 金山快盘服务器维护中,金山快盘为什么停止服务
  19. ChatGPT - 使用28原则快速学习的Prompt
  20. Aizu - 2224 Save your cats 最大生成树

热门文章

  1. 【GDB调试学习笔记】Makefile生成多个可执行文件
  2. 点云能量预测:KPConv点云输入方式
  3. ENVI入门系列教程---一、数据预处理---1.1基本操作--5.x以后的界面(新界面)
  4. 《深度学习Python实践》第17章——算法调参
  5. php数据库密码查询,php数据库查询及密码匹配的功能
  6. 大型分布式Java项目--宜立方商城
  7. h5红包雨代码_【多管闲事】非专业人士H5学习指北:从门还没入到放弃 | 叙一来闲...
  8. Android的JNI【实战教程】5⃣️---Android Studio 2.2 以上 NDK开发
  9. 刚刚!中科院主导的国产编程语言木兰负责人回应了!承认32位机器上,是基于Python二次开发!...
  10. batch normalization的原理和作用_【推荐算法】Deep amp; Cross Network模型原理和实践...