更新时间:2020-11-20 17:45:39 来源:极悦 浏览1312次
Java中提供了shop()方法来中断线程,但由于该方法过于暴力而被定义为过期方法。假如一条线程在修改一段数据时,且已经修改了一半,此时的你强行用shop()方法中断该线程后,数据处于一半修改过、一半未修改的状态,该数据就已经废了(且不会有任何提示)。于是,在Java中采用了新的interrupt方法来完成Java多线程中断机制。
Thread类定义了如下关于中断的方法:
线程对中断的反应
1.RUNNABLE:线程在运行或具备运行条件只是在等待操作系统调度
2.WAITING/TIMED_WAITING:线程在等待某个条件或超时
3.BLOCKED:线程在等待锁,试图进入同步块
4.NEW/TERMINATED:线程还未启动或已结束
public void Thread.interrupt() //中断线程
public boolean Thread.isInterrupted() //判断是否被中断
public static boolean Thread.interrupted() //判断是否被中断,且清除当前中断状态
public static void main(String[] args) throws InterruptedException {
Thread t1 = new Thread() {
@Override
public void run () {
while (true) {
Thread.yield();
}
}
};
t1.start();
Thread.sleep(2000);
ti.interrupt();
}
在这里虽然调用了interrupt()方法,但该线程并不会停下。因为该方法只是设置了一个中断状态,但该线程并未对此中断状态做出反应。
以下代码进行了对中断状态的处理。
public static void main(String[] args) throws InterruptedException {
Thread t1 = new Thread() {
@Override
public void run () {
while (true) {
if (Thread.currentThread().isInterrupted()){ //此方法返回中断状态,且不会清除该中断状态。
System.out.println("Interruted!");
breadk;
}
Thread.yield();
}
}
};
t1.start();
Thread.sleep(2000);
ti.interrupt();
}
但我们使用wait() 或者 sleep() 方法时要注意下:
首先得了解下Thread.sleep()函数:
public static native void sleep(long millis) throws InterruptedException
当该线程休眠时如果中断则会抛出该错误,此异常非运行时异常,必须捕获且处理。
public static void main(String[] args) throws InterruptedException {
Thread t1 = new Thread() {
@Override
public void run () {
while (true) {
if (Thread.currentThread().isInterrupted()){
//此方法返回中断状态,且不会清除该中断状态
System.out.println("Interruted!");
break;
}
try {
Thread.sleep(2000);
} catch (InterruptedException e) {
System.out.println("Interruted When Sleep");
// 设置中断状态
Thread.currentThread().interrupt();
}
Thread.yield();
}
}
};
t1.start();
Thread.sleep(2000);
t1.interrupt();
}
在catch语块中本可以进行中断退出,但我们没这么做,因为这样会破坏数据一致性和完整性(和直接使用shop()用异曲同工之妙)。所以我们在异常处理中必须重新设置中断状态(因为此时抛出异常后状态会被清除),让该线程完成工作后再退出。
那么我们如何正确地取消/关闭线程呢?
1. interrupt方法不一定会真正”中断”线程,它只是一种协作机制,如果 不明白线程在做什么,不应该贸然的调用线程的interrupt方法,以为这样就能取消线程。
2. 对于以线程提供服务的程序模块而言,它应该封装取消/关闭操作,提供单独的取消/关闭方法给调用者,类似于InterruptReadDemo中演示的cancel方法,外部调用者应该调用这些方法而不是直接调用interrupt。
3. Java并发库的一些代码就提供了单独的取消/关闭方法,比如说,Future接口提供了如下方法以取消任务:boolean cancel(boolean mayInterruptIfRunning);
4. 再比如,ExecutorService提供了如下两个关闭方法:
void shutdown();
List
5. Future和ExecutorService的API文档对这些方法都进行了详细说明,这是我们应该学习的方式。
以上就是Java多线程中断机制,总的来说,就是采用了interrupt方法来中断对应的线程。多线程作为Java中的重难点知识点,是我们学好Java的突破口,想要学好Java除了要付出时间和努力,还有有一个好的学习方法。本站的Java多线程教程里面能够给出系统地学习多线程的方法,助你快速学好Java多线程!
0基础 0学费 15天面授
Java就业班有基础 直达就业
业余时间 高薪转行
Java在职加薪班工作1~3年,加薪神器
工作3~5年,晋升架构
提交申请后,顾问老师会电话与您沟通安排学习