浅析java线程中断的办法


Posted in Javascript onJuly 29, 2018

中断线程相关的方法

中断线程有一些相应的方法,这里列出来一下。

注意,如果是Thread.method(),则代表是静态方法。如果是thread.method()则代表着是类方法

void thread.stop()

这个方法能中断正在运行的线程,但是已经不推荐使用了,在将来的版本或许弃用,因为强行中断运行中的线程,是不安全的。

void thread.interrupt()

如果正在运行wait(),sleep(),join()这三个方法阻塞了线程,那么将会使得线程抛出InterruptedException异常,这是一个中断阻塞的过程。如果是其它的正在运行的状态,那么将不会有任何影响,也不会中断线程,或者抛出异常,只会会打上一个中断线程的标志,是否中断线程,将由程序控制。

boolean thread.isInterrupted()

它会获取当前线程的标志,如果之前调用过thread.interrupt(),那么它的返回值是true。它的作用就是返回该线程是否有中断标志。多次调用这个方法的结果是一样的。

void Thread.interrupted()

与前面的方法不一样的是,这是一个静态方法,代表着不需要拿到线程对象就可以直接执行,所以它的作用是返回当前线程是否有中断标志。但是它的区别是,当调用这个方法之后,会清除程序的中断标志,就是如果当前线程已中断,第一次调用这个方法的返回值是true,第二次调用这个方法的返回值为false,因为调用方法时,会清除它的中断标志。

中断线程

for循环标记退出

package com.xiaojiezhu.thread;

/**
 * @author xiaojie.zhu
 */
public class ThreadBreak implements Runnable {

  @Override
  public void run() {
    for(int i = 0 ; i < 10000 ; i ++){
      boolean interruped = Thread.currentThread().isInterrupted();
      if(interruped){
        //有中断标记,中断
        break;
      }
      System.out.println(i);
    }

    System.out.println("over");
  }


  public static void main(String[] args) throws InterruptedException {
    Thread t = new Thread(new ThreadBreak());
    t.start();
    Thread.sleep(1);

    t.interrupt();
  }
}

打印结果如下

44
45
46
47
over

阻塞的退出线程

只要是在运行wait(),sleep(),join()的方法,它就会声明一个InterruptedException异常,也就是意味着这些方法并不是一定能执行完成,因为当调用线程的interrupt()方法时,就会中断这个阻塞的办法,从而进入到异常中,代码如下

package com.xiaojiezhu.thread;

/**
 * @author xiaojie.zhu
 */
public class ThreadBreak2 implements Runnable {
  @Override
  public void run() {
    try {
      Thread.sleep(20000);
      System.out.println("这段话不会输出");
    } catch (InterruptedException e) {
      //如果在sleep()的过程中调用了interrupt()方法,就会进入这里,因为会强行中断sleep()
      
      //这里打印出来的中断标记为false,因为只要进入了InterruptedException异常,中断标记就会被清除掉
      System.out.println("中断标记为:" + Thread.currentThread().isInterrupted());
      System.out.println("输出异常");
      e.printStackTrace();
    }
  }

  public static void main(String[] args) throws InterruptedException {
    Thread t = new Thread(new ThreadBreak2());
    t.start();

    Thread.sleep(100);

    t.interrupt();

    System.out.println("over");
  }
}

打印结果如下

over
中断标记为:false
输出异常
java.lang.InterruptedException: sleep interrupted
at java.lang.Thread.sleep(Native Method)
at com.xiaojiezhu.thread.ThreadBreak2.run(ThreadBreak2.java:10)
at java.lang.Thread.run(Thread.java:748)

注意:因为只要进入了InterruptedException异常,中断标记就会被清除掉

这里会衍生出另一种情况,就是如果在进入阻塞方法之前,就有了中断标记呢?会发生什么,就如下的代码:

for(int i = 0 ; i < 10000 ; i ++){
  System.out.println(i);
}
try {
  System.out.println("开始sleep");
  Thread.sleep(20000);
  System.out.println("结束sleep");

} catch (InterruptedException e) {
  e.printStackTrace();
}

实际上它会先执行完上面的for循环,因为for循环中是无法中止的,在进入sleep()的时候,瞬间就抛出异常

完整的测试代码如下

package com.xiaojiezhu.thread;

/**
 * @author xiaojie.zhu
 */
public class ThreadBreak3 implements Runnable {

  @Override
  public void run() {
    for(int i = 0 ; i < 10000 ; i ++){
      System.out.println(i);
    }
    try {
      System.out.println("开始sleep");
      Thread.sleep(20000);
      System.out.println("结束sleep");

    } catch (InterruptedException e) {
      e.printStackTrace();
    }

  }

  public static void main(String[] args) {
    Thread thread = new Thread(new ThreadBreak3());
    thread.start();

    thread.interrupt();
  }
}

打印结果如下

9997
9998
9999
开始sleep
java.lang.InterruptedException: sleep interrupted
  at java.lang.Thread.sleep(Native Method)
  at com.xiaojiezhu.thread.ThreadBreak3.run(ThreadBreak3.java:15)
  at java.lang.Thread.run(Thread.java:748)

使用stop()方法停止线程

thread.stop()方法是一个不安全的方法,已经不推荐使用了,但是在目前的代码中,还能正常使用,我们不推荐这样使用,但是这里介绍一下

package com.xiaojiezhu.thread;

/**
 * @author xiaojie.zhu
 */
public class ThreadBreak4 implements Runnable {
  @Override
  public void run() {
    System.out.println("进入线程");
    try {
      Thread.sleep(20000);
      System.out.println("结束线程");
    } catch (InterruptedException e) {
      e.printStackTrace();
    }

  }

  public static void main(String[] args) {
    Thread t = new Thread(new ThreadBreak4());
    t.start();
    try {
      Thread.sleep(200);

      t.stop();

      System.out.println("over");
    } catch (InterruptedException e) {
      e.printStackTrace();
    }
  }
}

打印结果如下

进入线程
over

Javascript 相关文章推荐
js封装可使用的构造函数继承用法分析
Jan 28 Javascript
Bootstrap每天必学之缩略图与警示窗
Nov 29 Javascript
jQuery实现的鼠标滑过弹出放大图片特效
Jan 08 Javascript
JS实现六位字符密码输入器功能
Aug 19 Javascript
JS实现的幻灯片切换显示效果
Sep 07 Javascript
获取当前月(季度/年)的最后一天(set相关操作及应用)
Dec 27 Javascript
浅谈键盘上回车按钮的js触发事件
Feb 13 Javascript
基于vue.js实现侧边菜单栏
Mar 20 Javascript
Vue.js实战之组件之间的数据传递
Apr 01 Javascript
详解vue使用插槽分发内容slot的用法
Mar 28 Javascript
详解如何在vue项目中使用layui框架及采坑
May 05 Javascript
js+canvas实现五子棋小游戏
Aug 02 Javascript
还不懂递归?读完这篇文章保证你会懂
Jul 29 #Javascript
如何在js代码中消灭for循环实例详解
Jul 29 #Javascript
Vue-cli3项目配置Vue.config.js实战记录
Jul 29 #Javascript
vue权限路由实现的方法示例总结
Jul 29 #Javascript
JS高级技巧(简洁版)
Jul 29 #Javascript
js运算符的一些特殊用法
Jul 29 #Javascript
不得不知的ES6小技巧
Jul 28 #Javascript
You might like
php empty()与isset()区别的详细介绍
2013/06/17 PHP
PHP面向对象程序设计之类常量用法实例
2014/08/20 PHP
常见PHP数据库解决方案分析介绍
2015/09/24 PHP
PHP使用redis消息队列发布微博的方法示例
2017/06/22 PHP
PHP基于timestamp和nonce实现的防止重放攻击方案分析
2019/07/26 PHP
myEvent.js javascript跨浏览器事件框架
2011/10/24 Javascript
js 判断浏览器使用的语言示例代码
2014/03/22 Javascript
让table变成exls的示例代码
2014/03/24 Javascript
jQuery异步加载数据并添加事件示例
2014/08/24 Javascript
JavaScript简介
2015/02/15 Javascript
微信小程序 开发指南详解
2016/09/27 Javascript
JS根据生日月份和日期计算星座的简单实现方法
2016/11/24 Javascript
微信小程序 增、删、改、查操作实例详解
2017/01/13 Javascript
详解VUE的状态控制与延时加载刷新
2017/03/27 Javascript
AugularJS从入门到实践(必看篇)
2017/07/10 Javascript
jQuery实现对网页节点的增删改查功能示例
2017/09/18 jQuery
Vue.js进阶知识点总结
2018/04/01 Javascript
Layui 设置select下拉框自动选中某项的方法
2018/08/14 Javascript
基于webpack4.X从零搭建React脚手架的方法步骤
2018/12/23 Javascript
如何在微信小程序里面退出小程序的方法
2019/04/28 Javascript
监控微信小程序中的慢HTTP请求过程详解
2019/07/05 Javascript
详解如何在Javascript和Sass之间共享变量
2019/11/13 Javascript
nodejs实现百度舆情接口应用示例
2020/02/07 NodeJs
vue实现按钮切换图片
2021/01/20 Vue.js
python实现定制交互式命令行的方法
2014/07/03 Python
Sanic框架流式传输操作示例
2018/07/18 Python
对python 树状嵌套结构的实现思路详解
2019/08/09 Python
使用python制作游戏下载进度条的代码(程序说明见注释)
2019/10/24 Python
Html5 webRTC简单实现视频调用的示例代码
2020/09/23 HTML / CSS
UNDONE手表官网:世界领先的定制手表品牌
2018/11/13 全球购物
JD Sports澳洲官网:英国领先的运动鞋和运动时尚零售商
2020/02/15 全球购物
SQL Server提供的3种恢复模型都是什么? 有什么区别?
2012/05/13 面试题
CSMA/CD介质访问控制协议
2015/11/17 面试题
生日宴会答谢词
2014/01/09 职场文书
语文教研活动总结
2014/07/02 职场文书
大学生党员个人总结
2015/02/13 职场文书