如何中断阻塞调用UDP socket的receive()[重复]
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了如何中断阻塞调用UDP socket的receive()[重复]相关的知识,希望对你有一定的参考价值。
这个问题在这里已有答案:
我有一个UDP服务器监听来自客户端的数据包。
socket = new DatagramSocket(port);
while (isListen) {
byte[] data = new byte[1024];
DatagramPacket packet = new DatagramPacket(data, 0, data.length);
socket.receive(packet);
}
receive()
方法将在收到数据包之前永远等待。是否有可能停止等待接收?我可以设置一个boolean
isListen
来阻止循环。另一方面,如果套接字正在等待,那么如果没有从客户端发送数据包,它将永远等待。
答案
您可以从另一个线程关闭套接字。然后在receive()中阻塞的线程将抛出IOException。
while (isListen) {
byte[] data = new byte[1024];
DatagramPacket packet = new DatagramPacket(data, 0, data.length);
try {
socket.receive(packet);
} catch(IOException e) {
continue;
}
}
void stopListening() { // Call me from some other thread
isListen = false;
socket.close();
}
另一答案
您需要使用setSoTimeout()方法设置套接字超时,并在超过超时时捕获SocketTimeoutException
的socket
方法抛出的receive()
。捕获异常后,您可以继续使用套接字接收数据包。因此,在循环中使用该方法允许您定期(根据超时设置)“中断”receive()
方法调用。
请注意,必须在进入阻止操作之前启用超时。
一个例子(w.r.t你的代码):
socket = new DatagramSocket(port);
socket.setSoTimeout(TIMEOUT_IN_MILLIS)
while (isListen) {
byte[] data = new byte[1024];
DatagramPacket packet = new DatagramPacket(data, 0, data.length);
while (true) {
try {
socket.receive(packet);
break;
} catch (SocketTimeoutException e) {
if (!isListen) {} // implement your business logic here
}
}
// handle the packet received
}
以上是关于如何中断阻塞调用UDP socket的receive()[重复]的主要内容,如果未能解决你的问题,请参考以下文章
即使在客户端ShutDown()之后,Socket.Receive也会阻塞