2013-10-21 139 views
-1

请参阅下面的代码。这是从Oracle教程页面的修改后的代码示例:Java线程优先

public class BadThreads { 
    static String message; 

private static class CorrectorThread extends Thread { 
    public void run() { 
     try { 
      sleep(1000); 
     } catch (InterruptedException e) {} 
     message = "Mares do eat oats."; 
     System.out.println("1: "+ message); 
    }  
} 

public static void main(String args[]) throws InterruptedException { 

    CorrectorThread c=new CorrectorThread(); 

    c.start(); 
    System.out.println("0: "+ message); 
    c.run(); 
    System.out.println("2: "+ message); 

    message = "Mares do not eat oats."; 
    System.out.println("3: "+ message); 

    Thread.sleep(2000); 
    System.out.println("4: "+ message); 
} 
} 

打印

0: null 
1: Mares do eat oats. 
1: Mares do eat oats. 
2: Mares do eat oats. 
3: Mares do not eat oats. 
4: Mares do not eat oats. 

和是好的。

当我在main方法注释掉

c.run(); 

,我得到

0: null 
2: null 
3: Mares do not eat oats. 
1: Mares do eat oats. 
4: Mares do eat oats. 

主要是前Ç执行怎么来的?线程c具有与其“父”线程相同的优先级主要

难道主要是可见的ç从而ç等待主要返回?这是没有道理的,但是我能想到的唯一的事情。

// ============================

编辑: 更换

c.run(); 

c.join(); 

为相同的效果和更精细的编程。

+0

http://arashmd.blogspot.com/2013/06/java-threading.html#synctr – 2013-10-21 12:27:24

+1

优先级只是一个提示,在许多情况下完全忽略,如果你不是'root'或'administrator'它只是很重要如果你的CPU使用率很高,我不建议你这样做。 –

+0

Peter Lawrey:我知道公平是保证避免饥饿的一件事 - 虽然不能保证等待时间最长的线程第一回合,但没有听到高CPU利用率(?) – Roam

回答

1

当您拨打c.run()时,它会执行运行功能并等待完成。等待时间也会涵盖线程时间并且在第一种情况下您会看到两个连续输出。在第二种情况下,线程启动并且主要运行与run函数平行,因为运行处于睡眠状态,并且它覆盖了主要的显示语句。

c.start()启动线程平行于主线程运行。调用运行函数,并在完成时移动到下一个语句。

+0

是的,是的。在这一天的这个时刻错过了时差。谢谢。 – Roam

+0

@格雷 - 他的回答在你编辑之前看起来不错。如果那当然好了。 – Roam

+0

@roam仍然感谢灰色,改善.... :) –

0

见联注释

CorrectorThread c=new CorrectorThread(); 

c.start(); // new thread started, but up to scheduler to decide when to give it a slice of time 
System.out.println("0: "+ message); 
c.run(); // ran in main thread 
System.out.println("2: "+ message); // as expected, message was set by the other thread 

message = "Mares do not eat oats."; 
System.out.println("3: "+ message); // as expected 

Thread.sleep(2000); 
System.out.println("4: "+ message); // as expected 

c.start()c.run()将是双方最终调用CorrectorThread#run(),但在不同的线程。这取决于Thread调度程序,它将首先到达那里。

在你不叫c.run()调度的例子有时间打电话给

System.out.println("0: "+ message); // null 

System.out.println("2: "+ message); // null 

其他线程有时间来初始化message之前。

+0

仔细阅读Q. – Roam

+0

@Roam这是一场比赛,一个Thread设置'message',另一个设置它。 –

+0

你的答案改变了。我已经评论过 - 最初的一个。 – Roam

4

线程的重点在于它们并行执行。所以主线程与校正器线程并行执行。由于校正器线程所做的第一件事是休眠1秒,因此主线程有足够的时间在校正器线程更改消息之前执行其指令。

+0

是的,时差。与我为zeeshan mughal写的评论一样。 – Roam

+0

好奇你为什么选择比这个更晚的答案,还有更差的@Roam。 – Gray

0

尝试这样的: -

public class BadThreads { 
    static String message; 

    private static class CorrectorThread extends Thread { 
     public void run() { 
      try { 
       sleep(1000); 
      } catch (InterruptedException e) {} 
      message = "Mares do eat oats."; 
      System.out.println("3: "+ message); 
     }  
    } 

    public static void main(String args[]) throws InterruptedException { 

     CorrectorThread c=new CorrectorThread(); 
     c.start(); 

     System.out.println("0: "+ message); 
     System.out.println("1: "+ message); 

     message = "Mares do not eat oats."; 
     System.out.println("2: "+ message); 

     Thread.sleep(2000); 
     System.out.println("4: "+ message); 
    } 
} 
+0

无法启动无法运行。 – Roam

+0

因此更新,同样请尝试 –

+0

请你解释一下,让其他人可以学习。只要放下未注释的代码就不会教任何东西。 – Gray

1

这是什么奇怪的家伙在这里,因为没有关于主线程保证进入的调用线程/方法的顺序第一或第二becasue。

第一个c.start()开始一个新的线程,这意味着主要继续它的工作。所以在第一种情况下,你有这样的事情

0000->thread main starts the bad thread | bad thread sleeps for 1 second 
     and prints the message value(null) 
0001->thread main runs the run() method | bad thread still is sleeping 
     with its thread 
0002-> both thread are sleeping .... 
0003->..... 
1000->either bad thread or main thread changes the message value to "Mares do eat oats." (not sure which goes first!) 
1001->thread main prints("1:" +message) | bad thread prints("1:" +message) 
1002->thread main prints("1:" +message) | bad thread has terminated X 
1003->thread main changes the message value to "Mares do not eat oats." 
1004->main threads prints the message again and sleeps for 2 seconds 
2004->main thread prints the message again. 

而在第二种情况下,没有呼叫run()由主线程,所以主线程不睡1秒如不良的线程做,只是尝试打印邮件并将其值更改为“Mares不吃燕麦”。并再次打印,然后休眠2秒钟,然后在1秒钟后(当主线程处于睡眠状态时)唤醒坏线程时,它改变消息的值并打印它,主线程在2秒后打印由坏线程改变的消息。

答案在这里,因为执行顺序,不保证哪个线程先行或后行。 this tutorial可能会帮助你的兄弟。