黑马程序员技术交流社区

标题: 关于join方法的一点疑问 [打印本页]

作者: 土突突    时间: 2014-5-1 00:36
标题: 关于join方法的一点疑问
本帖最后由 土突突 于 2014-5-3 12:21 编辑

无意中写错了一个程序,但是从中发现了一点问题,代码如下:
  1. class  JoinDemo
  2. {
  3.         public static void main(String[] args)
  4.         {
  5.            Textt t1=new Textt();
  6.            Test t2=new Test();
  7.            Thread th1=new Thread(t1);
  8.            Thread th2=new Thread(t2);
  9.            th2.start();
  10.            try{th1.join();} catch(InterruptedException e){System.out.println(e);}
  11.            th1.start();

  12.          }
  13. }

  14. class Textt implements Runnable
  15. {
  16.          public void run()
  17.          {
  18.               for(int i=0;i<100;i++)
  19.                       System.out.println(Thread.currentThread().getName()+"-------run--------"+i);
  20.           }
  21. }
  22. class Test implements Runnable
  23. {
  24.           public void run()
  25.           {
  26.                 for(int i=0;i<100;i++)
  27.                       System.out.println(Thread.currentThread().getName()+"-------------run--------"+i);
  28.           }

  29. }
复制代码
如上,本来在主函数中想先调用两个线程的start()方法,然后再th1.join( )看下效果。结果写成了上述代码。运行后发现两个线程仍然能交替运行。
在此有点小疑问。以下是我的个人看法...
th2先启动,当执行到th1的join()方法时主线程以及th2应该等待至th1执行完毕。但此时th1线程并没有被启动。还不具有抢夺CPU的能力。此时要么出现未知异常,要么程序会卡在此处一直等待th1的执行。
为什么还会一直出现两个线程交替运行的情况呢?


作者: Lin0411    时间: 2014-5-2 21:44
  1. 调用join()放生作用的条件:如果线程被生成了,但还未被起动,调用它的 join() 方法是没有作用的,将直接继续向下执行 。
  2. 在上面的代码中当th2和主线程启动后,顺序执行到th1.join()时th1并没有启动!!!
  3. 出现楼主的编译结果是正常的。
复制代码

作者: Lin0411    时间: 2014-5-2 21:46
  1. JDK中关于join的一段源码:
  2.     public final synchronized void join(long millis)    throws InterruptedException {  
  3.         long base = System.currentTimeMillis();  
  4.        long now = 0;  
  5.   
  6.         if (millis < 0) {  
  7.             throw new IllegalArgumentException("timeout value is negative");  
  8.         }  
  9.          
  10.         if (millis == 0) {  
  11.             while (isAlive()) {  
  12.                 wait(0);  
  13.             }  
  14.         } else {  
  15.             while (isAlive()) {  
  16.                 long delay = millis - now;  
  17.                 if (delay <= 0) {  
  18.                     break;  
  19.                 }  
  20.                 wait(delay);  
  21.                now = System.currentTimeMillis() - base;  
  22.             }  
  23.         }  
  24.     }  
  25. 也和好的说明了当线程没启动就调用join方法是不起作用的将直接向下顺序执行!!!
复制代码

作者: 土突突    时间: 2014-5-3 12:20
Lin0411 发表于 2014-5-2 21:46

受教了,谢谢
作者: ww384661784    时间: 2014-5-3 19:12
不错不错!!!!!!!!!!!!!!!!!!!!




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2