[抢海拾遗]java并发之线程中断
来源:互联网 发布:淘宝付款扣款2次 编辑:程序博客网 时间:2024/06/10 10:15
java线程启动比较容易,但是要停止却比较麻烦。JAVA在线程设计之初设计了大量的方法来控制线程的状态,如start、suspend、resume、stop、destroy等操作。后来由于在多线程开发环境中各种并发问题而被deprecated了。本文主要介绍一些线程的stop方法以及正确的中断线程方法。
Thread.stop
在一开始使用java时,要停止一个线程,有可能会误用线程的这个方法。虽然它一开始被加入jdk是为了停止线程而用,但是stop方法是线程不安全的,且其停止原理相当粗暴,通过直接抛出一个ThreadDead的异常来释放当前线程的所有锁,并且将线程停止。这种作法会导致该线程所操作的数据不一致,比如:当前线程为了更新某个数据,而获取了某个锁,然后在更新中途,调用stop时,然后另一个线程访问该对象时,就会拿到一个数据不一致的对象,导致错误。
那么能不能通过捕获ThreadDead异常,然后进行一些操作来保证线程安全地退出呢?理论上是可以的,但是这会加大并发编程中的难度,因为有两个原因导致了这种作法不能被实际使用:
- ThreadDead异常有可能在任何地方被抛出,如果你要捕获就需要在所有地方加上catch;
- ThreadDead异常有可能被迭代抛出,导致维持数据一致的操作无法进行。
因此一般不大会用stop来进行线程的结束。那么如何进行线程的优雅结束呢?
信号变量
通过一个变更来存储线程是否结束状态,如果检测到该状态为结束状态,则停止当前线程,如下:
public class MyThread extends Thread { private volatile boolean stoped = false; public void done() { stoped = true; } public void run() { while (!stoped) { // do something } }}
由于是多线程处理,所以最好加上vilatile,以此保证变量可见性,虽然大多数情况下,stoped变量晚点看到问题也不大。
上面的这种方法适合于那种可以不断地去查询变量状态的情况。但是如果线程被某些操作长时间锁住,如IO阻塞,则无法响应线程的停止请求,这个时候可以使用线程中断的另一机制:Interrupt。
Thread.interrupt
Thread.interrupt方法与Thread.stop方法不同之处在于,interrupt方法只是将线程的状态改为interrupted,来等待线程自身的中断策略来进行线程中断出来,并不会粗暴的抛出一个运行期异常来中断线程。这样就解决了stop的线程不安全的问题。但是同时通过Thread.interrupt调用后并不是会肯定能够马上停止当前线程,这依赖于线程自身的中断策略。
而与通过信号变量来中断线程相比,interrupt方法被一些阻塞方法所支持,所以能够在线程被阻塞住时,也能响应interrupt。但是不是所有的阻塞操作都支持,有一些阻塞方法就不支持,如下:
java的socket IO。由于Inputstream和Outputstream的read和write方法不支持中断,因此在这些操作被阻塞住时可以通过socket的close方法来抛出一个socketException来中断线程;
java NIO的同步IO。中断其interruptibleChannel,会抛出CloseByInterruptException,通过捕获来处理中断;
java NIO的异步IO。通过close方法抛出的CloseSelectorException来中断。
ExecutorService的中断
线程服务的中止有两个方法,一个是shutdown,一个是shutdownNow。shutdown的实现逻辑就是将线程池的状态改为shutdown,然后再遍历所有的线程,然后调用线程的interrupt来进行所有线程的中止。而shutdownNow的不同之处在于,它会记录当前已经提交但是未结束的线程,以期能够记录下来。
- [抢海拾遗]java并发之线程中断
- Java并发之线程中断
- 《Java并发编程》之线程中断与终止线程运行
- 《Java并发编程》之线程中断与终止线程运行
- Java 并发之中断
- 【Java并发编程】之二:线程中断(含代码)
- 【Java并发编程】之二:线程中断(含代码)
- 【Java并发编程】之二:线程中断(含代码)
- Java并发学习之三——线程的中断
- 【Java并发编程】之二:线程中断(含代码)
- 【Java并发编程】之二:线程中断(含代码)
- 【Java并发编程】之二:线程中断(含代码)
- 【Java并发编程】之二:线程中断(含代码)
- Java多线程与并发(四)之中断线程
- 【Java并发编程】之二:线程中断(含代码)
- 【Java并发编程】之二:线程中断(含代码)
- Java并发编程之二:线程的中断
- 【Java并发编程】之二:线程中断(含代码)
- grid flex用法
- [python] shutil模块
- 55个高质量的Magento主题,助你构建电子商务站点
- opencv imshow 显示灰色窗口
- securecrt颜色配置
- [抢海拾遗]java并发之线程中断
- android sqlite 触发器
- HTTP协议通信过程
- Android 操纵File查看文件大小,清理文件
- 创建异步 HTTP 处理程序
- cocos2d-x之OpenGL概述
- hibernate异常之--HibernateObjectRetrievalFailureException: No row with the given identifier exists
- OpenCV学习笔记(五十)——Algorithm类介绍(core)
- 对于集合中的自定义对象使用collections.sort 进行排序,需要实现compartor接口