中断(interrupt)表明线程应该停止正在执行的操作并执行其他操作。 完全由程序员决定线程如何响应中断,但是线程终止是很常见的。 这是本课中强调的用法。
线程通过在要中断线程的Thread对象上调用interrupt,来发送中断。 为了使中断机制正常工作,被中断的线程必须支持自己的中断。
支持中断
线程如何支持自己的中断?这取决于它当前正在做什么。如果线程经常调用抛出InterruptedException的方法,则在捕获该异常后,它仅从run方法返回。例如,假设SleepMessages示例中的中央消息循环位于线程Runnable对象的run方法中。然后可以对其进行如下修改,以支持中断:
for (int i = 0; i < importantInfo.length; i++) {// Pause for 4 secondstry {Thread.sleep(4000);} catch (InterruptedException e) {// We've been interrupted: no more messages.return;}// Print a messageSystem.out.println(importantInfo[i]);}
许多抛出InterruptedException的方法(例如sleep)旨在取消其当前操作,并在收到中断时立即返回。
如果线程长时间运行而没有调用抛出InterruptedException的方法怎么办? 然后,它必须定期调用Thread.interrupted,如果收到中断,则返回true。 例如:
for (int i = 0; i < inputs.length; i++) {heavyCrunch(inputs[i]);if (Thread.interrupted()) {// We've been interrupted: no more crunching.return;}}
在这个简单的示例中,代码仅测试了中断,如果已接收到中断,则退出线程。在更复杂的应用程序中,抛出InterruptedException可能更有意义:
if (Thread.interrupted()) {throw new InterruptedException();}
中断状态标志
中断机制使用内部标志(称为中断状态(interrupt status))实现。调用Thread.interrupt设置此标志。当线程通过调用静态方法Thread.interrupted检查中断时,将清除中断状态。一个线程用于查询另一线程的中断状态的非静态方法isInterrupted不会更改中断状态标志。
按照惯例,任何通过抛出InterruptedException而退出的方法都会清除中断状态。但是,总是有可能通过另一个线程调用interrupt,再次立即设置中断状态。
