具有套接字I / O阻塞操作的中断/停止线程

时间:2012-09-07 09:13:52

标签: java multithreading sockets

在我的服务器应用程序的某个时刻,我想停止一些执行I / O阻塞操作的线程。

例如,其中一个具有以下run()方法:

public void run() {
    System.out.println("GWsocket thread running");

    int len;
    byte [] buffer = new byte[1500];
    try {
        this.in  = new DataInputStream(this.socket.getInputStream());
        this.out = new DataOutputStream(this.socket.getOutputStream());
        running = true;

        while (running){
            len = in.read (buffer);
            if (len < 0)
                running = false;
            else
                parsepacket (buffer, len);
        }

    }catch (IOException ex) {
        System.out.println("GWsocket catch IOException: "+ex);
    }finally{
        try {
            System.out.println("Closing GWsocket");
            fireSocketClosure();
            in.close();
            out.close();
            socket.close();
        }catch (IOException ex) {
            System.out.println("GWsocket finally IOException: "+ex);
        }
    }
}

如果我想停止运行此代码的线程,我该怎么办?

Here他们展示了如何做(如何停止等待很长时间的线程(例如,输入)?),但我不明白他们的意思用:

  

要使这项技术发挥作用,任何捕获的方法都至关重要   中断异常,并不准备立即处理它   重申例外。我们说重申而不是重新抛出,   因为并不总是可以重新抛出异常。如果   捕获InterruptedException的方法未声明为throw   这个(已检查)异常,然后它应该“重新中断”   以下咒语:Thread.currentThread()。interrupt();

任何人都可以给我一些提示吗?一些代码示例将非常受欢迎。

2 个答案:

答案 0 :(得分:6)

您可以添加类似

的方法
public void close() throws IOException {
    this.socket.close();
}

并且任何阻塞IO操作都将抛出SocketException。

您可能希望设置一个类似closed的标记,您可以检查是否预期会抛出异常。

BTW:您不能确定在读取时会得到离散数据包。阅读所需内容并使用BufferedInputStream提高效率要好得多。如果您不需要解析内容,则只读取块,例如从套接字复制到文件。

e.g。你的读取只能得到一个字节,或者得到一个数据包的结束和另一个数据包的开始。

答案 1 :(得分:6)

Peter Lawrey描述的一个解决方案,也看到here是关闭套接字。

使用nio,您还可以使用SocketChannel interruptible并允许应用standard interrupt model of Java

调用Thread对象的interrupt方法会抛出InterruptedException,甚至会阻止阻塞IO操作。