【发布时间】:2011-04-02 06:26:44
【问题描述】:
JDK 文档说,如果线程被中断而当前阻塞在 InterruptibleChannel 的 io 操作中,则通道将关闭并抛出 ClosedByInterruptException。但是,我在使用 FileChannel 时会得到不同的行为:
public class Main implements Runnable {
public static void main(String[] args) throws Exception {
Thread thread = new Thread(new Main());
thread.start();
Thread.sleep(500);
thread.interrupt();
thread.join();
}
public void run() {
try {
readFile();
} catch (IOException ex) {
ex.printStackTrace();
}
}
private void readFile() throws IOException {
FileInputStream in = new FileInputStream("large_file");
FileChannel channel = in.getChannel();
ByteBuffer buffer = ByteBuffer.allocate(0x10000);
for (;;) {
buffer.clear();
// Thread.currentThread().interrupt();
int r = channel.read(buffer);
if (Thread.currentThread().isInterrupted()) {
System.out.println("thread interrupted");
if (!channel.isOpen())
System.out.println("channel closed");
}
if (r < 0)
break;
}
}
}
这里,当线程被中断时,即使通道已经关闭,read() 调用也会正常返回。不会抛出异常。此代码打印“线程中断”和“通道关闭”,然后在下一次调用 read() 时抛出 ClosedChannelException。
我想知道这种行为是否被允许。据我了解文档,read() 应该正常返回而不关闭通道或关闭通道并抛出 ClosedByInterruptException。正常返回并关闭频道似乎不对。我的应用程序的问题是,当执行 io 的 FutureTask 被取消时,我在其他地方得到了一个意外且看似无关的 ClosedChannelException。
注意:当线程在进入 read() 时已经被中断时,将按预期抛出 ClosedByInterruptException。
我在使用 64 位服务器虚拟机(JDK 1.6.0 u21,Windows 7)时看到了这种行为。谁能证实这一点?
【问题讨论】:
标签: java multithreading exception io