【发布时间】:2021-01-28 17:36:39
【问题描述】:
主/调用线程等待其他线程完成任务的最佳方式是什么?我想出了两个选择;可能还有更多。
选项 1 - Thread.sleep()
new Thread(() -> System.out.println("Executed task 1")).start();
new Thread(() -> System.out.println("Executed task 2")).start();
Thread.sleep(1000);
选项 2 - 闩锁
CountDownLatch latch = new CountDownLatch(2);
new Thread(() -> {
System.out.println("Executed task 1");
latch.countDown();
}).start();
new Thread(() -> {
System.out.println("Executed task 2");
latch.countDown();
}).start();
latch.await(1, TimeUnit.SECONDS);
选项 3 - CompletableFuture
CompletableFuture<Void> future1 = CompletableFuture.runAsync(() -> System.out.println("Executed task 1"));
CompletableFuture<Void> future2 = CompletableFuture.runAsync(() -> System.out.println("Executed task 2"));
CompletableFuture.allOf(future1, future2).join();
选项 4 - ??
【问题讨论】:
-
Thread.sleep()对线程同步毫无用处。如果您发现自己将它用于此目的,那么您做错了什么。句号。 -
不要以如图所示的显式方式使用线程。由于 Java 5 中并发框架的到来,使用它比手动使用线程更受青睐。
-
@AndrewHenle 是对的,不要使用 sleep()。您可以改为 .join() 两个线程。如果您必须等待某些线程完成/完成(run() 结束),.join() 就是设计的。顺便说一句,它也使HB边缘。 CountDownLatch 适用于分步场景。您的示例也可以,但是在更复杂的业务逻辑中,在线程中执行,只需确保在任何情况下都调用了latch.countDown()(例如,使用 finally 部分)。至于 CompletableFuture,我会将它们用于一些非常短暂的工作。对于一项特定的长期工作,我更喜欢使用明确的线程。
标签: java multithreading java-threads