2013-02-10 26 views
1

我看到有趣的行为。我这段代码运行Java线程:在启动后调用Thread对象的run()方法

public class ThreadsTest { 

    public static void main(String[] args) { 
     Runnable mr = new MyRunnable(); 
     Thread t1 = new Thread(mr); 
     Thread t2 = new Thread(mr); 
     t1.setName("first"); 
     t2.setName("second"); 
     t1.start(); 
     t2.start(); 
     t1.run(); 
    } 
} 

class MyRunnable implements Runnable { 
    public void run() { 
    for (int i=0; i < 2; i++) { 
     System.out.println("Running: " + Thread.currentThread().getName()); 
    } 
    } 
} 

我得到的输出是:

Running: first 
Running: first 
Running: second 
Running: second 

我期待看到类似这样的东西:

Running: first 
Running: first 
Running: second 
Running: second 
Running: main 
Running: main 

有谁知道为什么我不在我的输出中的某处可以看到Running: main。谢谢。

+1

我不知道你为什么期望。你能解释一下吗? – AHungerArtist 2013-02-10 04:22:07

+1

对Thread对象调用run()方法't1.run()'应调用MyRunnable类中的run方法。它应该输出当前正在运行的线程是主线程。对Thread对象调用run()方法的行为与调用任何其他对象上的任何方法的行为相同。我希望我的回答对你有意义。 – robonerd 2013-02-10 04:28:49

回答

8

这个解释有点微妙。

Thread.run()方法的默认行为被描述为运行提供的Runnable(如果存在),否则什么也不做。

微妙之处在于,当线程退出时,exit()方法会“积极”地清除参考字段以防止存储泄漏。 (这里是the source ... 720行。)看起来,当你在main中调用t1.run()时,线程退出了,所以这个调用是没有操作的。

当然,输出取决于main线程在子线程退出之前是否再次运行......这将取决于您的平台;例如JVM和OS级别的线程调度程序执行的操作以及可用的内核数量。

+4

+1,但可能值得补充的是它可能*显示'Running:main',具体取决于线程调度(可能还有代码重新排序?不太清楚它的含义)。 – 2013-02-10 04:26:53

+0

Stephen C的解释确实有道理。谢谢。 Brian Roach确实如此,你无法预测调度如何工作。我只是不明白为什么运行永远不会执行。多谢你们。 – robonerd 2013-02-10 04:35:50

0

我刚刚在我的机器上运行了您的代码,并在输出中看到“Running:main”。

+0

相同: 运行:主要 运行:第二 运行:第一 运行:第二 运行:主要 运行:第一 – msangel 2013-02-10 04:24:03

+2

是...输出将是依赖于平台。看到我的答案。 – 2013-02-10 04:31:53

相关问题