有人可以在Java Thread类中解释join方法吗?

时间:2015-12-10 11:57:44

标签: java multithreading synchronization

    public final synchronized void join(long millis) throwsInterruptedException {
    long base = System.currentTimeMillis();
    long now = 0;

    if (millis < 0) {
        throw new IllegalArgumentException("timeout value is negative");
    }

    if (millis == 0) {
        while (isAlive()) {
            wait(0);
        }
    } else {
        while (isAlive()) {
            long delay = millis - now;
            if (delay <= 0) {
                break;
            }
            wait(delay);
            now = System.currentTimeMillis() - base;
        }
    }
}

wait(0)如何让主线程等到它完成为止。线程正在调用等待自己?据我所知,它必须锁定自己来调用wait()方法?完成后如何通知主线程?

3 个答案:

答案 0 :(得分:3)

documentation解释了逻辑:

  

此实现使用以this.wait为条件的this.isAlive次调用循环。当线程终止时,将调用this.notifyAll方法。建议应用程序不要在wait个实例上使用notifynotifyAllThread

所以这个实现依赖于Thread对象不只是代表一个线程,而且像Java中的任何其他对象一样的对象。因此,它继承自Object,具有自己的监视器并且可以同步,在其上有线程wait等。

  

它必须锁定自己才能调用wait()方法吗?

是。事实上,这种方法被声明为 synchronized 。所以它在Thread实例本身上同步。进入内部后,您将拥有Thread实例的监视器。然后当调用wait时,你放弃它,所以其他线程可以做同样的事情。

这可能有点令人困惑。您当前运行的线程是线程A.您在线程B上使用join。此处正在同步的对象是线程B的实例,这会导致线程A等待,直到调用notifyAll为止。同样(B)实例。

当线程B完成时,它会在自己的实例上调用notifyAll。因此,将通知在线程B的实例上wait中阻塞的任何线程。

答案 1 :(得分:1)

  

据我所知,它必须锁定自己才能调用wait()方法?

不在本身上,而是在Thread对象上。调用者确实锁定Thread对象。请注意,t.join()是一种synchronized方法。

  

主线程完成后如何通知主线程?

不要对Thread线程之间的区别感到困惑。 Thread实例是一个堆对象,程序用它来启动和管理代码中执行线程的生命周期。它的方法通常由其他线程调用,而不是它正在管理的线程。

如果主题A调用t.join(),它将锁定对象t,然后它将调用t.wait()所需的次数,直到t的状态为{ Thread.State.TERMINATED

请记住,在每个t.wait()调用中,锁定被释放,然后在wait()返回之前重新获取。

在由t管理的主题中,它执行的最后一件事是,它将t的状态设置为TERMINATED,然后调用{{1 }}。这将唤醒线程A.

答案 2 :(得分:0)

obj.wait()导致当前线程休眠,直到另一个线程调用obj.notify()。

t.join() - 导致当前线程等到线程&#39; t&#39;饰面