引言:
相信大家对
CyclicBarrier并不陌生,当一个线程调用了CyclicBarrier的await方法时,线程阻塞,直到指定数量的线程都执行完await方法后才唤醒所有线程。那么CyclicBarrier的代码底层是如何实现的呢?它和CountDownLatch有什么区别呢?
很显然,
CyclicBarrier底层是使用ReentrantLock中的getCondition得到Condition,然后调用await和signalAll方法控制线程的阻塞和唤醒。
一、CyclicBarrier用法
1
//初始化时,传入参数int parties------new Cyclicbarrier(int parties);//相当于一个计数器,每执行一个线程parties-1,直到parties == 0,线程不再阻塞。
2
//线程的run方法里面加入cyclicBarrier的await的方法,阻塞等待所有线程执行完毕再向下执行
3
@Override
4
public void run() {
5
System.out.println("线程"+Thread.currentThread().getName()+"正在写入数据...");
6
try {
7
Thread.sleep(5000); //以睡眠来模拟写入数据操作
8
System.out.println("线程"+Thread.currentThread().getName()+"写入数据完毕,等待其他线程写入完毕");
9
cyclicBarrier.await();
10
} catch (InterruptedException e) {
11
e.printStackTrace();
12
}catch(BrokenBarrierException e){
13
e.printStackTrace();
14
}
15
System.out.println("所有线程写入完毕,继续处理其他任务...");
16
}
二、await方法源码:
1
/**
2
* Waits until all {@linkplain #getParties parties} have invoked
3
* {@code await} on this barrier.
4
*
5
* <p>If the current thread is not the last to arrive then it is
6
* disabled for thread scheduling purposes and lies dormant until
7
* one of the following things happens:
8
* <ul>
9
* <li>The last thread arrives; or
10
* <li>Some other thread {@linkplain Thread#interrupt interrupts}
11
* the current thread; or
12
* <li>Some other thread {@linkplain Thread#interrupt interrupts}
13
* one of the other waiting threads; or
14
* <li>Some other thread times out while waiting for barrier; or
15
* <li>Some other thread invokes {@link #reset} on this barrier.
16
* </ul>
17
*
18
* <p>If the current thread:
19
* <ul>
20
* <li>has its interrupted status set on entry to this method; or
21
* <li>is {@linkplain Thread#interrupt interrupted} while waiting
22
* </ul>
23
* then {@link InterruptedException} is thrown and the current thread's
24
* interrupted status is cleared.
25
*
26
* <p>If the barrier is {@link #reset} while any thread is waiting,
27
* or if the barrier {@linkplain #isBroken is broken} when
28
* {@code await} is invoked, or while any thread is waiting, then
29
* {@link BrokenBarrierException} is thrown.
30
*
31
* <p>If any thread is {@linkplain Thread#interrupt interrupted} while waiting,
32
* then all other waiting threads will throw
33
* {@link BrokenBarrierException} and the barrier is placed in the broken
34
* state.
35
*
36
* <p>If the current thread is the last thread to arrive, and a
37
* non-null barrier action was supplied in the constructor, then the
38
* current thread runs the action before allowing the other threads to
39
* continue.