前言
本篇文章是一个系列文章,旨在简单、快速的重拾 多线程 的基础用法,深入浅出的捋清楚多线程的边边角角。
今天聊得话题是: 如何优雅的暂停线程~
一、停止线程
停止线程是在多线程开发时很重要的技术点。停止线程并不像break语句那样干脆,需要一些技巧性的处理。
在 java 中有以下3种方法可以终止正在运行的线程:
- 1)使用退出标志,使线程正常退出,也就是当run()方法完成后线程停止。
- 2)使用stop()方法强行终止线程,但是不推荐使用这个方法,因为该方法已经作废过期,使用后可能产生不可预料的结果。
- 3)使用interrupt()方法中断线程。
1.1、暴力法停止线程
调用stop()方法时会抛出 java.lang.ThreadDeath 异常,但在通常的情况下,此异常不需要显示地捕捉。
方法stop()已经被作废,因为如果强制让线程停止线程则有可能使一些清理性的工作得不到完成。另外一个情况就是对锁定的对象进行了“解锁”,导致数据得不到同步的处理,出现数据不一致的情况。示例如下:
运行结果:
bb AA
1.2、异常法停止线程
使用interrupt()方法并不会真正的停止线程,调用interrupt()方法仅仅是在当前线程中打了一个停止的标记,并不是真的停止线程。
那我们如何判断该线程是否被打上了停止标记,Thread类提供了两种方法。
interrupted() 测试当前线程是否已经中断。
isInterrupted() 测试线程是否已经中断。
interrupted() 方法 不止可以判断当前线程是否已经中断,而且可以会清除该线程的中断状态。而对于isInterrupted() 方法,只会判断当前线程是否已经中断,不会清除线程的中断状态。
仅靠上面的两个方法可以通过while(!this.isInterrupted()){}对代码进行控制,但如果循环外还有其它语句,程序还是会继续运行的。这时可以抛出异常从而使线程彻底停止。示例如下:
打印结果:
2490
2491
2492
2493
已经是停止状态了!
注意
如果线程在sleep()状态下被停止,也就是线程对象的run()方法含有sleep()方法,在此期间又执行了thread.interrupt() 方法,则会抛出java.lang.InterruptedException: sleep interrupted异常,提示休眠被中断。
1.3、return法停止线程
return法很简单,只需要把异常法中的抛出异常更改为return即可。代码如下:
不过还是建议使用“抛异常”来实现线程的停止,因为在catch块中可以对异常的信息进行相关的处理,而且使用异常能更好、更方便的控制程序的运行流程,不至于代码中出现多个return,造成污染。
尾声
因为篇幅原因,这篇文章暂时到此就停止了。下篇文章《Java多线程没什么难的:深入前的浅出》