登录  /  注册
首页 > Java > java教程 > 正文

Java怎样中断一个运行中的线程(1)

黄舟
发布: 2016-12-30 13:19:45
原创
906人浏览过

编程人员在编程过程中,多线程呈现出了一组新的难题,而如何中断一个正在运行的线程则是难题之一。本文中,作者将讲述相关的方法。

程序是很简易的。然而,在编程人员面前,多线程呈现出了一组新的难题,如果没有被恰当的解决,将导致意外的行为以及细微的、难以发现的错误。

在本篇文章中,我们针对这些难题之一:如何中断一个正在运行的线程。

背景中断(interrupt)一个线程意味着在该线程完成任务之前停止其正在进行的一切,有效地中止其当前的操作。线程是死亡、还是等待新的任务或是继续运行至下一步,就取决于这个程序。虽然初次看来它可能显得简单,但是,你必须进行一些预警以实现期望的结果。你最好还是牢记以下的几点告诫。

首先,忘掉thread.stop方法。虽然它确实停止了一个正在运行的线程,然而,这种方法是不安全也是不受提倡的,这意味着,在未来的java版本中,它将不复存在。

一些轻率的家伙可能被另一种方法thread.interrupt所迷惑。尽管,其名称似乎在暗示着什么,然而,这种方法并不会中断一个正在运行的线程(待会将进一步说明),正如listing a中描述的那样。它创建了一个线程,并且试图使用thread.interrupt方法停止该线程。 thread.sleep()方法的调用,为线程的初始化和中止提供了充裕的时间。线程本身并不参与任何有用的操作。

class Example1 extends Thread {
            boolean stop=false;
            public static void main( String args[] ) throws Exception {
            Example1 thread = new Example1();
            System.out.println( "Starting thread..." );
            thread.start();
            Thread.sleep( 3000 );
            System.out.println( "Interrupting thread..." );
            thread.interrupt();
            Thread.sleep( 3000 );
            System.out.println("Stopping application..." );
            //System.exit(0);
            }
            public void run() {
            while(!stop){
            System.out.println( "Thread is running..." );
            long time = System.currentTimeMillis();
            while((System.currentTimeMillis()-time < 1000)) {
            }
            }
            System.out.println("Thread exiting under request..." );
            }
            }
登录后复制

如果你运行了Listing A中的代码,你将在控制台看到以下输出:

Starting thread...
Thread is running...
Thread is running...
Thread is running...
Interrupting thread...
Thread is running...
Thread is running...
Thread is running...
Stopping application...
Thread is running...
Thread is running...
Thread is running...
.....................
登录后复制

甚至,在Thread.interrupt()被调用后,线程仍然继续运行。

真正地中断一个线程

中断线程最好的,最受推荐的方式是,使用共享变量(shared variable)发出信号,告诉线程必须停止正在运行的任务。线程必须周期性的核查这一变量(尤其在冗余操作期间),然后有秩序地中止任务。Listing B描述了这一方式。

Listing B
class Example2 extends Thread {
  volatile boolean stop = false;
  public static void main( String args[] ) throws Exception {
    Example2 thread = new Example2();
   System.out.println( "Starting thread..." );
   thread.start();
   Thread.sleep( 3000 );
   System.out.println( "Asking thread to stop..." );
   thread.stop = true;
   Thread.sleep( 3000 );
   System.out.println( "Stopping application..." );
   //System.exit( 0 );
  }
  public void run() {
    while ( !stop ) {
     System.out.println( "Thread is running..." );
      long time = System.currentTimeMillis();
      while ( (System.currentTimeMillis()-time < 1000) && (!stop) ) {
      }
    }
   System.out.println( "Thread exiting under request..." );
  }
}
登录后复制

运行Listing B中的代码将产生如下输出(注意线程是如何有秩序的退出的)

Starting thread...
Thread is running...
Thread is running...
Thread is running...
Asking thread to stop...
Thread exiting under request...
Stopping application...
登录后复制

虽然该方法要求一些编码,但并不难实现。同时,它给予线程机会进行必要的清理工作,这在任何一个多线程应用程序中都是绝对需要的。请确认将共享变量定义成volatile 类型或将对它的一切访问封入同步的块/方法(synchronized blocks/methods)中。

到目前为止一切顺利!但是,当线程等待某些事件发生而被阻塞,又会发生什么?当然,如果线程被阻塞,它便不能核查共享变量,也就不能停止。这在许多情况下会发生,例如调用Object.wait()、ServerSocket.accept()和DatagramSocket.receive()时,这里仅举出一些。

他们都可能永久的阻塞线程。即使发生超时,在超时期满之前持续等待也是不可行和不适当的,所以,要使用某种机制使得线程更早地退出被阻塞的状态。

很不幸运,不存在这样一种机制对所有的情况都适用,但是,根据情况不同却可以使用特定的技术。在下面的环节,我将解答一下最普遍的例子。

 以上就是Java怎样中断一个运行中的线程(1)的内容,更多相关内容请关注PHP中文网(www.php.cn)!

智能AI问答
PHP中文网智能助手能迅速回答你的编程问题,提供实时的代码和解决方案,帮助你解决各种难题。不仅如此,它还能提供编程资源和学习指导,帮助你快速提升编程技能。无论你是初学者还是专业人士,AI智能助手都能成为你的可靠助手,助力你在编程领域取得更大的成就。
来源:php中文网
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
最新问题
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责申明 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送
PHP中文网APP
随时随地碎片化学习
PHP中文网抖音号
发现有趣的

Copyright 2014-2024 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号