问题一,datagramPacket中的setLength和setData中的data长度冲突了怎么办?
答,length可以短于缓冲区长度,但不可长于缓冲区长度。
datagramPacket有五个构造方法:
DatagramPacket(byte[] buf, int length)
构造 DatagramPacket
,用来接收长度为 length
的数据包。
DatagramPacket(byte[] buf, int length, InetAddress address, int port) 构造数据报包,用来将长度为 length 的包发送到指定主机上的指定端口号。 |
DatagramPacket(byte[] buf, int offset, int length) 构造 DatagramPacket ,用来接收长度为 length 的包,在缓冲区中指定了偏移量。 |
DatagramPacket(byte[] buf, int offset, int length, InetAddress address, int port) 构造数据报包,用来将长度为 length 偏移量为 offset 的包发送到指定主机上的指定端口号。 |
DatagramPacket(byte[] buf, int offset, int length, SocketAddress address) 构造数据报包,用来将长度为 length 偏移量为 offset 的包发送到指定主机上的指定端口号。 |
DatagramPacket(byte[] buf, int length, SocketAddress address) 构造数据报包,用来将长度为 length 的包发送到指定主机上的指定端口号。 |
其中 length不能超过buf的长度,buf这个缓冲区是绝对的,offset和length只是用来辅助缓冲区来定位当前需要发送的数据范围,所以offset和length的值都不能与缓冲区buf产生冲突,否则会报非法参数异常。
问题二,如果datagramSocket与datagramPacket都没有指定目的地址,那么这时候datagramSocket.send(),数据包会被发送到哪里?
答,在没有打开broadcast的情况下,数据包将不会被发送,或者说发送者不负责数据包的安全到达,不负责考虑接收者是否存在,
问题二,如果datagramSocket与datagramPacket指定了不同的目的地址,那么这时候datagramSocket.send(),数据包会被发送到哪里?
答,
public void send(DatagramPacket pack) throws IOException { checkOpen(); ensureBound(); InetAddress packAddr = pack.getAddress(); if (address != null) { // The socket is connected if (packAddr != null) { if (!address.equals(packAddr) || port != pack.getPort()) { throw new IllegalArgumentException("Packet address mismatch with connected address"); } } else { pack.setAddress(address); pack.setPort(port); } } else { // not connected so the target address is not allowed to be null if (packAddr == null) { throw new NullPointerException("Destination address is null"); } } impl.send(pack); }
由以上源码可知,datagramSocket.send()实际上完成了一个两方目标地址的核验,并以datagramSocket的地址为基准,毕竟如果datagramSocket上的地址表示已经连接的目标主机,所以,当两者的目的地址产生冲突时,就会IllegalArgumentException