Java中等待线程执行完毕

来源:互联网 发布:基本编程 编辑:程序博客网 时间:2024/06/07 02:50

前言:前一段时间在做项目的时候,某段代码中用到了多线程,该处代码需要开启多个线程,待这几个线程执行完毕后再接着执行后续的流程。现将可采用的方法记录如下。


要达到上述的描述的情形,可以使用Thread的join()方法,也可以使用java.util.concurrent包中的CountDownLatch类。具体如下:

一、使用Thread.join()方法

该方法在JDK API中的解释为“等待该线程终止”,存在三个方法重载,如下:
void join();
void join(long millis); // 等待该线程终止的最长时间为millis毫秒
void join(long millis, int nanos); // 等待该线程终止的最长时间为millis毫秒+nanos纳秒

代码如下:

package threadTest;import java.util.Vector;import java.util.concurrent.*;/** * Created by worm0527 on 2017/7/17. */public class ThreadTest extends Thread {    // 线程名称    private String threadName;    // 线程休眠时间    private int sleepSec;    ThreadTest(String threadName, int sleepSec) {        super(threadName);        this.sleepSec = sleepSec;        start();// 在构造方法中启动线程    }    @Override    public void run() {        long starttime = System.currentTimeMillis();        System.out.println(Thread.currentThread().getName() + " running...");        try {            // 休眠制定时间(单位:秒)            TimeUnit.SECONDS.sleep(sleepSec);        } catch (InterruptedException e) {            e.printStackTrace();        }        System.out.println(Thread.currentThread().getName() + " run at " + (System.currentTimeMillis() - starttime) + " ms");    }    public static void main(String[] args) throws InterruptedException {        long starttime = System.currentTimeMillis();        System.out.println("Thread main running...");        Vector<Thread> threadVector = new Vector<Thread>();        for (int i = 1; i < 5; i++) { // 开启四个线程            Thread t = new ThreadTest("Thread" + i, i);            threadVector.add(t);        }        for (Thread t : threadVector) { // 循环调用线程join()方法,等待线程结束            t.join();        }        System.out.println("Thread main End");        System.out.println("Thread main run at " + (System.currentTimeMillis() - starttime) + " ms");    }}

运行结果:

运行结果

二、使用CountDownLatch类

主要使用了该类的await()和countDown()两个方法。await()阻塞线程,直到计数器归零或者线程被中断,调用countDown()来递减计数器。

代码如下:

package threadTest;import java.util.concurrent.CountDownLatch;import java.util.concurrent.TimeUnit;/** * Created by worm0527 on 2017/7/18. */public class ThreadTest1 extends Thread {    // 线程名称    private String threadName;    // 线程休眠时间    private int sleepSec;    private CountDownLatch latch; // 线程类中持有CountDownLatch对象的引用    public ThreadTest1(String threadName, int sleepSec, CountDownLatch latch) {        super(threadName);        this.sleepSec = sleepSec;        this.latch = latch;        start();// 在构造方法中启动线程    }    @Override    public void run() {        long starttime = System.currentTimeMillis();        System.out.println(Thread.currentThread().getName() + " running...");        try {            // 休眠制定时间(单位:秒)            TimeUnit.SECONDS.sleep(sleepSec);        } catch (InterruptedException e) {            e.printStackTrace();        }        System.out.println(Thread.currentThread().getName() + " run at " + (System.currentTimeMillis() - starttime) + " ms");        latch.countDown();    }    public static void main(String[] args) throws InterruptedException {        long starttime = System.currentTimeMillis();        System.out.println("Thread main running...");        CountDownLatch latch = new CountDownLatch(4); // 共四个子线程        for (int i = 1; i < 5; i++) {            new ThreadTest1("Thread" + i, i, latch);        }        latch.await(); // 阻塞,直到线程计数归零        System.out.println("Thread main End");        System.out.println("Thread main run at " + (System.currentTimeMillis() - starttime) + " ms");    }}

运行结果:

运行结果

1 0