网络通信-1(InetAddress、UDP、TCP、DatagramPacket、DatagramSocket、UDP通信示例)
1. 网络通信
1.1三要素:
- IP地址:网络中设备表示,可用主机名
- 端口号,用于表示进程的逻辑地址
- 传输协议:通讯的规则,常见的协议:TCP、IP
1.2 Socket
为网络编程提供的一种机制。
通信的两端都有Socket。
网络通信其实就是Socket间的通信,数据在两个Socket之间通过IO传输。
2. InetAddress

所有已实现的接口:
Serializable
直接已知子类:
Inet4Address(32位), Inet6Address(128位)
表示互联网协议 (IP) 地址。
- IP 地址是 IP 使用的 32 位或 128 位无符号数字,它是一种低级协议,UDP 和 TCP 协议都是在它的基础上构建的。
- InetAddress 的实例包含 IP 地址,还可能包含相应的主机名(取决于它是否用主机名构造或者是否已执行反向主机名解析)。
- 地址类型:
- 单播:单个接口的标识符。发送到单播地址的数据包被交付给由该地址标识的接口。
- 多播:一组接口(通常属于不同的节点)的标识符。发送到多播地址的数据包被交付给由该地址标识的所有接口。
- 主机名解析:
- 主机名到 IP 地址的解析:通过使用本地机器配置信息和网络命名服务(如域名系统(Domain Name System,DNS)和网络信息服务(Network Information Service,NIS))来实现。要使用的特定命名服务默认情况下是本地机器配置的那个。对于任何主机名称,都返回其相应的 IP 地址。
- 反向名称解析:意味着对于任何 IP 地址,都返回与 IP 地址关联的主机。
InetAddress 类提供将主机名解析为其 IP 地址(或反之)的方法。
2.1 方法
static InetAddress getByName(String host):在给定主机名的情况下确定主机的 IP 地址。
- host:输出后是主机名/IP地址
- IP:输出后是/IP地址
- 有异常抛出:UnknownHostException
static InetAddress getLocalHost():返回本地主机
String getHostName():获取此 IP 地址的主机名。
String getHostAddress():返回 IP 地址字符串(以文本表现形式)。
2.2 使用
import java.net.InetAddress;
import java.net.UnknownHostException;public class Test{public static void main(String[] args) throws UnknownHostException{InetAddress local=InetAddress.getLocalHost();InetAddress remote=InetAddress.getByName("www.baidu.com");System.out.println("本地IP地址是:"+local.getHostAddress());System.out.println("百度的IP地址是:"+remote.getHostAddress());System.out.println("百度的主机名是:"+remote.getHostName());}
}
运行结果:
成功
3. UDP
User Datagram Protocol
用户数据包协议
是无连通协议:在发送数据时,数据的发送端和接收端不建立逻辑连接
消耗资源少,通信效率高
用于音频、视频和普通数据的传输
不保证数据完整性
数据包大小在64K
4. TCP
TAransmission Control Protocol
传输控制协议
面向连接的通信协议
在传输数据前,先在发送端和接受选建立逻辑连接,再传输数据。
提供了两台计算机之间的可靠的无差错疏忽传输
4.1 三次握手
创立连接
- C向S发出连接请求
- S向C回送一个响应
- C向S发送确认消息
可保证传输数据的安全性
eg.下载文件
5. DatagramPacket
![]()
此类表示数据报包。 UDP通信中发送或者接受的数据
数据报包用来实现无连接包投递服务(类似于集装箱)。
每条报文仅根据该包中包含的信息从一台机器路由到另一台机器。
从一台机器发送到另一台机器的多个包可能选择不同的路由,也可能按不同的顺序到达。
不对包投递做出保证。
5.1 构造方法
DatagramPacket(byte[] buf,int length): 构造DatagramPacket,用来接收长度为length的数据包。
- 接收端的,只需要接收的一个字节数组来存放收到的数据,无需知道数据的来源
DatagramPacket(byte[] buf,int length,InetAddress address,int port): 构造数据报包,用来将长度为length的包发送到指定主机上的指定端口号。
- 接收字节数组,指定发送目的端的IP地址和端口号。
5.2 方法
InetAddress getAddress():发挥某台机器的IP地址。此数据报将要发往该机器或者是从该机器接收到的。
int getPort():返回某远程主机的端口号。此数据报将要发往该主机或者是从该主机接收到的。
byte[] getData():返回数据缓冲区
int getLength():返回将要发送或接收到的数据的长度。
6. DatagramSocket
![]()
此类表示用来发送和接收数据报包的套接字。
数据报套接字是包投递服务的发送或接收点(类似于码头)。
每个在数据报套接字上发送或接收的包都是单独编址和路由的。从一台机器发送到另一台机器的多个包可能选择不同的路由,也可能按不同的顺序到达。
在 DatagramSocket 上总是启用 UDP 广播发送。为了接收广播包,应该将 DatagramSocket 绑定到通配符地址。在某些实现中,将 DatagramSocket 绑定到一个更加具体的地址时广播包也可以被接收。
DatagramSocket s=new DatagramSocket(null);
s.bind(new InetSocketAddress(8888));
这等价于:
DatagramSocket s=new DatagramSocket(8888);
两个例子都能创建能够在UDP 8888端口上接收广播的DatagramSocket。
6.1 构造方法
DatagramSocket():构造数据报套接字并将其绑定到本地主机上任何可用的端口。
DatagramSocket(int port):创建数据报套接字并将其绑定到本地主机上的指定端口。
- 接收端:徐志鼎一个端口号,可监听指定的端口;
- 发送端:可指定端口号;也可不指定,系统会分配一个没有被其他网络程序使用的端口号
6.2 方法
void receive(DatagramPacket p): 从此套接字接收数据报包。
void send(DatagramPacket p):从此套接字发送数据报包。
7. UDP网络程序
7.1 发送端
- 创建DatagramSocket对象
- 创建DatagramPacket对象,并封装数据
- 发送数据
- 释放流资源
import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;public class Test{public static void main(String[] args) throws IOException{DatagramSocket sendSocket=new DatagramSocket();byte[] buffer="hello,UDP".getBytes();DatagramPacket dp=new DatagramPacket(buffer,buffer.length,InetAddress.getByName("***本机IP地址***"),8888);sendSocket.send(dp);sendSocket.close();}
}
7.2 接收端
- 创建DatagramSocket对象
- 创建DatagramPacjet对象
- 接收数据存储到DatagramPacket对象中
- 获取DatagramPacket对象的内容
- 释放流资源
import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;public class DemoTest{public static void main(String[] args) throws IOException {DatagramSocket receiveSocket=new DatagramSocket(8888);byte[] buffer=new byte[1024];DatagramPacket dp=new DatagramPacket(buffer,1024);receiveSocket.receive(dp);InetAddress ipAddress=dp.getAddress();String ip=ipAddress.getHostAddress();byte[] data=dp.getData();int length=dp.getLength();String datastr=new String(data,0,length);System.out.println("IP地址:"+ip+",数据是:"+datastr);receiveSocket.close();}
}
运行结果:

7.3 分析
发送端
DatagramPacket dp=new DatagramPacket(buffer,buffer.length,InetAddress.getByName("***本机IP地址***"),8888);如果此句中,主机名错,UnknowHostException;端口号错,可正常发出,接收端收不到。
无连接的协议,无接收端也可运行。
接收端
启动两次接收端:
- 第一次正常
- 第二次:BindException,端口号已绑定。
- 端口号不可重复,它是一个进程在内存中的地址

本文来自互联网用户投稿,文章观点仅代表作者本人,不代表本站立场,不承担相关法律责任。如若转载,请注明出处。 如若内容造成侵权/违法违规/事实不符,请点击【内容举报】进行投诉反馈!
