Java中的柵欄(CyclicBarrier)
是一種用于協調多個線程并發工作的同步輔助類。與CountDownLatch不同,CyclicBarrier允許一組線程相互等待,直到所有線程都到達一個共同的屏障點(barrier)后,才繼續執行。CyclicBarrier的主要特點是可以重復使用,因此適用于需要多個階段的任務同步。
示例代碼:
import java.util.concurrent.BrokenBarrierException;
import java.util.concurrent.CyclicBarrier;public class CyclicBarrierWithActionExample {public static void main(String[] args) {int threadCount = 3;CyclicBarrier barrier = new CyclicBarrier(threadCount, new BarrierAction());for (int i = 0; i < threadCount; i++) {new Thread(new TaskWithAction(barrier)).start();}}
}class BarrierAction implements Runnable {@Overridepublic void run() {System.out.println("所有線程都到達屏障點,執行barrierAction。");}
}class TaskWithAction implements Runnable {private final CyclicBarrier barrier;TaskWithAction(CyclicBarrier barrier) {this.barrier = barrier;}@Overridepublic void run() {try {System.out.println(Thread.currentThread().getName() + " 正在執行任務...");// 模擬任務執行Thread.sleep((long) (Math.random() * 1000));System.out.println(Thread.currentThread().getName() + " 到達屏障點。");barrier.await(); // 等待其他線程到達屏障點System.out.println(Thread.currentThread().getName() + " 繼續執行。");} catch (InterruptedException | BrokenBarrierException e) {e.printStackTrace();}}
}
在這個例子中,當所有線程都到達屏障點時,會首先執行BarrierAction中的任務,然后再繼續執行線程的后續代碼。
一個模擬多階段的任務,每個階段所有線程都需要同步后才能進入下一個階段。每個階段完成后,還會執行一個額外的屏障操作。
import java.util.concurrent.BrokenBarrierException;
import java.util.concurrent.CyclicBarrier;public class MultiStageTaskExample {public static void main(String[] args) {int threadCount = 4;int stageCount = 3;CyclicBarrier barrier = new CyclicBarrier(threadCount, new BarrierAction());for (int i = 0; i < threadCount; i++) {new Thread(new Worker(barrier, stageCount)).start();}}
}class Worker implements Runnable {private final CyclicBarrier barrier;private final int stageCount;Worker(CyclicBarrier barrier, int stageCount) {this.barrier = barrier;this.stageCount = stageCount;}@Overridepublic void run() {try {for (int stage = 1; stage <= stageCount; stage++) {// 模擬每個階段的任務System.out.println(Thread.currentThread().getName() + " 正在執行第 " + stage + " 階段任務...");Thread.sleep((long) (Math.random() * 1000)); // 模擬任務執行時間// 等待其他線程到達屏障點System.out.println(Thread.currentThread().getName() + " 到達第 " + stage + " 階段屏障點。");barrier.await();}} catch (InterruptedException | BrokenBarrierException e) {e.printStackTrace();}}
}class BarrierAction implements Runnable {@Overridepublic void run() {System.out.println("所有線程都已到達屏障點,準備進入下一階段...");}
}
跳轉到:
CountDownLatch
信號量(Semaphore)