首頁 >Java >java教程 >Java CountDownLatch完成非同步回呼範例程式碼分享

Java CountDownLatch完成非同步回呼範例程式碼分享

黄舟
黄舟原創
2017-03-23 10:29:431804瀏覽

這篇文章主要介紹了Java CountDownLatch完成非同步回呼實例詳解的相關資料,需要的朋友可以參考下

Java CountDownLatch完成異步回呼實例詳解

實例程式碼:

public class AsyncDemo {

  private static void doSomeTask() {
    System.out.println("Hello World");
  }

  private static void onCompletion() {
    System.out.println("All tasks finished");
  }

  public static void main(String[] args) {
    ExecutorService executor = Executors.newCachedThreadPool();
    final CountDownLatch latch = new CountDownLatch(2);

    executor.execute(new Task(latch));
    executor.execute(new Task(latch));

    executor.execute(() -> {
      try {
        latch.await();
      } catch (InterruptedException e) {
        e.printStackTrace();
      }
      onCompletion();
    });
    executor.shutdown();
  }

  private static class Task implements Runnable {

    /**
     * CountDownLatch 是JDK提供的一个简单的线程监测工具
     * 基于简单的计数,调用countDown()方法表明当前线程已经终止
     * 在监测线程中调用await()方法,该方法会一直挂起直到所有其它线程终止
     */
    private final CountDownLatch latch;

    public Task(CountDownLatch latch) {
      this.latch = latch;
    }

    @Override
    public void run() {
      try {
        doSomeTask();
      } catch (Exception e) {
        e.printStackTrace();
      } finally {
        latch.countDown();
      }
    }
  }
}

這裡有兩點需要補充:

1.如果你是用main方法啟動的線程,這種呼叫方法是沒有問題的,JDK會確保所有執行緒都終止以後main方法才退出。但如果main方法不是非同步任務的啟動者(如JUnit,Spring,Tomcat),一旦啟動之後laucher將會失去對執行緒的控制。如在JUnit中laucher提交完任務後就會被認為所有流程已完成,其它執行緒會被強行終止。

2.正因為如此,請根據環境使用正確的Executor。例如,在web環境中,應該選用tomcat(或Spring)管理的線程池作為Executor,這樣才能確保web應用對於異步任務的整個生命週期具有控制權;如果你選用JDK的線程池有什麼後果呢?任務也許可以正常執行,當一旦你終止web-app,正在執行的非同步線程並不會被正常kill掉,並由此造成記憶體洩漏或其它不可預見的後果。

以上是Java CountDownLatch完成非同步回呼範例程式碼分享的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn