首先打开源码查看join()方法:
1,没有参数的。可以看到join()方法调用同类中的一个有参join()方法,并传递参数0。
public final void join() throws InterruptedException {
join(0);
}
2.有一个long类型参数的join()方法使用了synchroinzed修饰,说明这个方法同一时刻只能被 一个实例或者方法调用。由于,传递的参数为0,所以,程序会进入如下代码的红色部分,在代码中以while循环的方式来判断当前线程是否已经启动处于活跃状态,如果已经启动处于活 跃状态,则调用同类中的wait()方法,并传递参数0。
public final synchronized void join(long millis)throws InterruptedException { 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()方法如下:public final native void wait(long timeout) throws InterruptedException;
wait()方法是一个本地方法,通过JNI的方式调用JDK底层的方法来使线程等待执行完成。
需要注意的是,调用线程的wait()方法时,会使主线程处于等待状态,等待子线程执行完成后再次向下 执行。也就是说,在ThreadSort02类的main()方法中,调用子线程的join()方法,会阻塞main()方法 的执行,当子线程执行完成后,main()方法会继续向下执行,启动第二个子线程,并执行子线程的业务 逻辑,以此类推。
3.这是两个参数的,增加了两个参数的判断,这样保证传进来的值不会有危害性。实际上最后一行还是调用了上面一个参数的方法。
public final synchronized void join(long millis, int nanos)throws InterruptedException {
if (millis < 0) {
throw new IllegalArgumentException("timeout value is negative");
}
if (nanos < 0 || nanos > 999999) {
throw new IllegalArgumentException(
"nanosecond timeout value out of range");
}
if (nanos >= 500000 || (nanos != 0 && millis == 0)) {
millis++;
}
join(millis);
}