代码之家  ›  专栏  ›  技术社区  ›  rouble

停止不被中断的线程

  •  3
  • rouble  · 技术社区  · 15 年前

    我有一个线程,它坐在对象输出流中读取对象:

    public void run() {
        try {
            ois = new ObjectInputStream(clientSocket.getInputStream());
    
            Object o;
            while ((o = ois.readObject()) != null) {
                //do something with object
            }
        } catch (Exception ex) {
            //Log exception
        }
    }
    

    readObject不会抛出InterruptedException,据我所知,当这个线程被中断时不会抛出异常。如何停止此线程?

    3 回复  |  直到 13 年前
        1
  •  3
  •   Tom Hawtin - tackline    15 年前

    呼叫 close 在套接字输入流上。您应该能够从另一个线程完成这项工作。

        2
  •  2
  •   Bob Cross n8wrl    13 年前

    看来 clientSocket 是您唯一的外部可见引用。从另一个线程调用 clientSocket.close()

    这将迫使 ObjectInputStream throw the IOException on the readObject() 打电话。它会触发你的catch块,让你退出循环。

    重读你的问题,你说 readObject 不会引发InterruptedException。在这一点上你是正确的:我正在寻找 读取对象 现在,它也不是 throws 它也没有明确地隐藏 InterruptedException .

    你应该总是能够触发决赛 catch (Exception ex) 通过调用 objectReadingThread.interrupt() 从另一个线程(或任何你命名你的阅读线程)。引用 Javadoc :

    如果该线程在wait()的调用中被阻塞,则等待(long), 或对象类或join()的wait(long,int)方法, join(long)、join(long,int)、sleep(long)或sleep(long,int)方法 该类的中断状态将被清除,它将 接收InterruptedException。

    如果此线程在I/O操作中被中断 然后通道关闭,线程的中断状态 将被设置,线程将收到CloseDBYInterruptException。

    如果该线程在选择器中被阻塞,则该线程的中断 状态将被设置,它将立即从选择中返回 操作,可能带有非零值,就像选择器的 已调用唤醒方法。

    如果前面的条件都不成立,那么这个线程的中断 将设置状态。

    如果这不起作用,我会调查“对对象做点什么”阻塞,并尝试找到一个异常接收器,它正在消耗您的中断并忽略它。

        3
  •  0
  •   digital_infinity    13 年前

    你可以试着抓住 InterruptedIOException . 我不知道在你的特定情况下是否有帮助,但它是处理此类案件最清晰的Java方式。

    我正在处理一个惊人的案例,尽管以某种神奇的方式捕捉到IOException,但EOFEException是不受注意的,所以我发现你的答案也很有趣。在另一种情况下,尽管InterruptException不能是: link to unexpected InterruptException . 这些情况有一些共同的问题,异常处理接近I/O操作。