【java】【多線程】等待開啓的多個線程都執行完成,再做事情,怎麼實現 《轉》

本文轉自: https://www.cnblogs.com/sxdcgaq8080/p/9456006.html

 

怎麼能有效保證高併發下的庫存和銷量的一致性呢?【具體實現方法:https://www.cnblogs.com/sxdcgaq8080/p/9454161.html

 

====

那麼好,在這個接口中,開啓多線程模擬了多個用戶請求同時到達的狀況,現在想在多個線程都執行完了以後再統一返回結果給前臺,哪些請求成功了,哪些請求失敗了。

====

所以現在的需求是怎麼能實現 等待多個線程都執行完了以後再做事情~~~

===================================================================================================================================

其實想要實現這個需求:等待多個線程執行完了,再做事情。

有兩種方法,可以應對不同的情況:

分別是CountDownLatchCyclicBarrier

===================================================================================================================================

CountDownLatch和CyclicBarrier簡單比較:

 

 

CountDownLatch

CyclicBarrier

軟件包

java.util.concurrent

java.util.concurrent

適用情景

主線程等待多個工作線程結束

多個線程之間互相等待,直到所有線程達到一個障礙點(Barrier point)

主要方法

CountDownLatch(int count) (主線程調用)

初始化計數

CountDownLatch.await (主線程調用)

阻塞,直到等待計數爲0解除阻塞

CountDownLatch.countDown

計數減一(工作線程調用)

CyclicBarrier(int parties, Runnable barrierAction) //初始化參與者數量和障礙點執行Action,Action可選。由主線程初始化

CyclicBarrier.await() //由參與者調用

阻塞,直到所有線程達到屏障點

等待結束

各線程之間不再互相影響,可以繼續做自己的事情。不再執行下一個目標工作。

在屏障點達到後,允許所有線程繼續執行,達到下一個目標。可以重複使用CyclicBarrier

異常

 

如果其中一個線程由於中斷,錯誤,或超時導致永久離開屏障點,其他線程也將拋出異常。

其他

 

如果BarrierAction不依賴於任何Party中的所有線程,那麼在任何party中的一個線程被釋放的時候,可以直接運行這個Action。

If(barrier.await()==2)

{

//do action

}

 

CountDownLatch 使用示例代碼:

主線程調用

工作線程調用

 

 


package com.sxd.swapping.utils;

import org.junit.Test;

import java.util.concurrent.CountDownLatch;

public class ThreadTest {


    /**
     * 主線程
     */
    @Test
    public  void  test(){

        //開啓10個多線程
        int threadCount = 10;

        //所有線程阻塞,然後統一開始
        CountDownLatch begin = new CountDownLatch(1);

        //主線程阻塞,直到所有分線程執行完畢
        CountDownLatch end = new CountDownLatch(threadCount);

        //開始多線程
        begin.countDown();
        for (Integer i = 0; i < threadCount; i++) {
            Runnable runnable = dealSomeThing(i,begin,end);
            new Thread(runnable).start();
        }

        //多個線程都執行結束
        try {
            end.await();
            System.out.println("多個線程都執行結束,可以做自己的事情了");
        } catch (InterruptedException e) {
            e.printStackTrace();
            System.out.println("多線程執行中出錯了,涼涼了!!!");
        }
    }


    /**
     * 工作線程
     * 本方法  是在構造多線程要做的事情
     *
     * =====================可以做的事===================
     * 當然可以傳入ConcurrentHashMap之類的線程安全的 類
     * 來記錄線程中的處理結果之類的
     * 最後 在多線程都執行完了以後 就可以對處理結果進行操作了
     * ==================================================
     *
     * @param threadNum 當前線程編號
     * @param begin
     * @param end
     * @return
     */
    private Runnable dealSomeThing(int threadNum, CountDownLatch begin, CountDownLatch end){
        Runnable runnable = new Runnable() {
            @Override
            public void run() {

                try {
                    System.out.println("線程"+threadNum+":--------------------->開始工作");
                    begin.await();

                    System.out.println("線程"+threadNum+"做具體的事情,比如去service調用 具體的方法做什麼操作之類的");

                    end.countDown();
                    System.out.println("線程"+threadNum+":--------------------->結束工作");
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }

            }
        };
        return runnable;
    }




}

 

 

最後實現的結果:

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章