Java - readObject() 和 setSoTimeout()

6

因此,我在客户端编写了一个线程,它尝试从套接字流中readObject()

只要客户端保持连接,该线程就会一直运行。

客户端的GUI可以关闭与服务器的连接。如果客户端决定通过单击“断开连接”菜单选项来断开连接(这不会退出客户端程序),则套接字将关闭并且isConnected将设置为false。

由于客户端读取线程尝试从流中readObject(),而连接可以通过GUI关闭,因此我将超时设置为250ms (setSoTimeout(250))。

@Override
public void run()
{
  this.connection = this.connectionHandler.getSocket();
  while(connectionHandler.isConnected())
  {
    this.readCircle();
  }
  this.connectionHandler.setReadTaskRunning(false);
}

private void readCircle()
{
  try
  {
    this.connection.setSoTimeout(250);
    this.connectionHandler.readData(); //this uses readObject().
  }
 catch(SocketTimeoutException timeout){}
 catch(...){}

我知道readObject()会阻塞,为了检查客户端是否仍然连接,我用while包装它,每隔一段时间检查一次客户端套接字是否仍然连接。

现在我的问题是:

如果readObject()开始传递一个对象给服务器,尝试读取它,但在处理超时时发生,那么流上的数据是否会“损坏”,因为它被取消了。 或者我应该让readObject()阻塞,并在GUI线程想要关闭套接字时捕获异常。

我对套接字不是很有经验,也许我的方法根本就是错误的。


1
isConnected()如果对等方断开连接,则不会返回false。您必须捕获和处理EOFException。 - user207421
是的,你说得对。在 catch(...){} 中,我必须捕获一堆异常。EOFException 的捕获将会调用 forceDisconnect() 来关闭客户端上的资源,并且调整用户界面元素。 - Jonas Bräuer
1个回答

2

当Socket读取超时时,readObject()将抛出SocketTimeoutException异常。您可能无法重复使用该ObjectInputStream,并且该流可能会因其当前位置大部分未定义而受到损坏。

这个问题可能只能通过关闭和重新打开连接来解决。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接