<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          多線程之countDownLatch

          共 5468字,需瀏覽 11分鐘

           ·

          2021-07-13 00:55

          前言

          原本是昨天分享countDownLatch相關(guān)知識(shí)點(diǎn)的,但是昨天粗略看寫(xiě)了,發(fā)現(xiàn)自己對(duì)countDownLatch的認(rèn)知還不夠,所以就半道分享了常用的三種多線程線程安全解決方案的性能比較,雖然過(guò)程中翻車(chē)了,但是還是有收獲的,畢竟發(fā)現(xiàn)了自己之前的認(rèn)知問(wèn)題,也不虧。今天又去看了下count的相關(guān)知識(shí),然后做了一個(gè)小demo,感覺(jué)有點(diǎn)眉目了,所以我們來(lái)繼續(xù)看countDownLatch。

          countDownLatch

          countDownLathjdk1.5引入的一個(gè)新特性,它的出現(xiàn)主要是為了解決某些應(yīng)用場(chǎng)景下多線程運(yùn)行順序的問(wèn)題。我們?cè)诙xcountDownLatch的時(shí)候,需要指定它的count大小,它就是通過(guò)這個(gè)count來(lái)控制多線程運(yùn)行順序的。

          它有兩個(gè)核心的方法countDownawait,countDown的作用是當(dāng)線程執(zhí)行完后把count減一,只能用一次;await方法是判斷count是否減為0,這個(gè)方法本身是阻塞的,如果count不是0await后面的代碼是不會(huì)被執(zhí)行的。

          接下來(lái),我們通過(guò)一段示例代碼來(lái)看下countDownLatch的基本用法:

          public class Example {
              private static AtomicInteger count = new AtomicInteger(0);
              private static final int SIZE_FIRST = 100;
              private static final int SIZE_SECOND = 50;

              public static void main(String[] args) throws InterruptedException {
                  ExecutorService executorService = Executors.newCachedThreadPool();
                  final CountDownLatch countDownLatch = new CountDownLatch(SIZE_FIRST);
                  for (int i = 0; i < SIZE_FIRST; i++) {
                      executorService.execute(new Task1(countDownLatch));
                  }
                  countDownLatch.await();
                  final CountDownLatch countDownLatch2 = new CountDownLatch(SIZE_SECOND);
                  for (int i = 0; i < SIZE_SECOND; i++) {
                      executorService.execute(new Task2(countDownLatch2));
                  }
                  countDownLatch2.await();
                  for (int i = 0; i < SIZE_SECOND; i++) {
                      executorService.execute(new Task3());
                  }
                  executorService.shutdown();
              }


              static class Task1 implements Runnable {
                  private final CountDownLatch countDownLatch;

                  Task1(CountDownLatch countDownLatch) {
                      this.countDownLatch = countDownLatch;
                  }


                  @Override
                  public void run() {
                      System.out.println("Task1: " + count.getAndIncrement());
                      this.countDownLatch.countDown();
                  }
              }

              static class Task2 implements Runnable {
                  private final CountDownLatch countDownLatch;

                  public Task2(CountDownLatch countDownLatch) {
                      this.countDownLatch = countDownLatch;
                  }

                  @Override
                  public void run() {
                      System.out.println("Task2: " + count.getAndIncrement());
                      this.countDownLatch.countDown();
                  }
              }

              static class Task3 implements Runnable {
                  @Override
                  public void run() {
                      System.out.println("Task3: " + count.getAndIncrement());
                  }
              }

          }

          這里我分別定義了三個(gè)線程,前兩個(gè)線程構(gòu)造的時(shí)候都需要傳入countDownLatch,然后在run方法的尾部執(zhí)行countDown方法,也就是每啟動(dòng)一個(gè)線程,count減一。

          我們這里還定義了兩個(gè)countDownLatch,初始值分別是10050,他們分別對(duì)應(yīng)線程task1task2的執(zhí)行次數(shù)。

          在線程task1task2之間我們執(zhí)行第一個(gè)countDownLatchawait方法,控制線程task1task2的執(zhí)行順序,確保線程task1先執(zhí)行;

          在線程task2和線程task3之間我們執(zhí)行第二個(gè)countDownLatchawait方法,控制線程task2task3的執(zhí)行順序,確保線程task2先執(zhí)行。

          然后,我們運(yùn)行上面的代碼,會(huì)得到如下結(jié)果:

          在以上結(jié)果中,我們可以看到,不論你執(zhí)行多少次,線程運(yùn)行順序都是task1、task2task3,當(dāng)然await方法之前的執(zhí)行順序我們是沒(méi)有辦法控制的。

          總結(jié)

          從上面演示結(jié)果來(lái)看,countDownLatch主要是用來(lái)控制多線程運(yùn)行順序的,特別適合多個(gè)線程協(xié)同運(yùn)行但是有順序要求的業(yè)務(wù),更多應(yīng)用場(chǎng)景大家有時(shí)間可以好好去研究下,我們今天的內(nèi)容就到這里吧!

          - END -


          瀏覽 42
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  中文天堂资源在线 | 天天综合天天添夜夜添狠狠添 | 午夜性福利| 黄色成人网站在线免费看 | 国产成人精品久久 |