如何在另一个线程仍在运行时停止主线程

3
我在我的主方法中启动了t1线程,并希望停止主线程,但是我的t1线程仍在运行。这是否可能?如何实现?
public static void main(String[] args) 
{
    Thread t1=new Thread()
    {
      public void run()
      {
          while(true)
          {
              try
              {
                  Thread.sleep(2000);
                  System.out.println("thread 1");

              }
              catch(Exception e)
              {}
          }             
      }
    };

    t1.start();    
}

System.exit(0);会停止整个应用程序,那么你如何知道线程t1仍在运行? - Abimaran Kugathasan
是的,我知道这种方法会决定应用程序。但是我只想停止主线程。这不可能吗? - Ahmad Vatani
4个回答

6
当Java程序启动时,一个线程立即开始运行。通常称之为程序的线程,因为它是在程序开始时执行的线程。主线程有两个重要作用:
• 它是其他“”线程将产生的线程。 • 它必须是最后一个停止执行的线程。当主线程停止时,程序终止。
还有一件事,在所有非守护线程死亡(守护线程是一个标记为setDaemon(true)的线程)时,程序终止。
这里有一个简单的代码片段,用于说明差异。尝试使用setDaemon中的true和false值进行测试。
public class DaemonTest {
    public static void main(String[] args) {
        new WorkerThread().start();
        try {
            Thread.sleep(7500);
        } catch (InterruptedException e) {}
        System.out.println("Main Thread ending") ;
    }
}

public class WorkerThread extends Thread {
    public WorkerThread() {
        setDaemon(false) ;   // When false, (i.e. when it's a user thread),
                // the Worker thread continues to run.
                // When true, (i.e. when it's a daemon thread),
                // the Worker thread terminates when the main 
                // thread terminates.
    }

    public void run() {
        int count=0 ;
        while (true) {
            System.out.println("Hello from Worker "+count++) ;
            try {
                sleep(5000);
            } catch (InterruptedException e) {}
        }
    }
}

3

常规线程可以防止虚拟机正常终止(即通过达到主方法的末尾 - 您在示例中未使用 System#exit(),该方法将根据文档终止虚拟机)。

为了使线程不会防止正常的VM终止,必须在启动线程之前通过Thread#setDaemon(boolean)将其声明为守护线程。

在您的示例中 - 当主线程达到其代码的末尾(在t1.start()之后),它将死亡,并且VM - 包括t1-在t1到达其代码的末尾时死亡(在while(true)后,也就是从未或异常终止)。

请参阅此问题,另一个类似问题的答案文档


谢谢您的回答,我用两个T1线程测试了我的问题,并在T1内定义了T2,然后停止了T1并发现T2仍在运行,但我想知道主线程的情况。 - Ahmad Vatani
从你的回答中我理解,在t1.start()之后只有t1线程在运行,我原以为主线程会在System.exit()结束。 - Ahmad Vatani
1
不,System.exit() 明确终止整个虚拟机。一个线程到达其代码路径的末尾只是从该虚拟机的活动线程集合中删除,然后检查是否还有其他非守护线程正在运行。如果没有,则会终止自身。如果有,则会继续运行。System.exit() 不涉及任何操作,除非被显式调用(由您) :) - hiergiltdiestfu

0

System.exit(0) 会退出当前程序。

"Thread.join()" 方法可能会帮助您实现所需的功能。


我相信Thread.join()会强制主线程等待直到所有其他线程完成执行。在这种情况下,他似乎停止了主线程,而子线程仍在运行。如果是这种情况,Thread.join()将无法帮助他。 - svjn

0

在任何其他线程正在运行时,您不能停止主线程(即所有从主线程衍生出来的子线程)。您可以使用函数Thread.join()使主线程等待其他线程执行。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接