天天看點

java.util.concurrent.Phaser了解

import java.util.concurrent.Phaser;

public class PhaserTest implements Runnable{
	
	public PhaserTest(Phaser phaser){
		this.phaser = phaser;
	}

	//Phaser這個類主要是針對于多階段注冊的任務的多線程工具類.
	//以下是個人了解,沒看API源碼.
	//顧名思義這個類中會存在類似的兩個變量來控制注冊和階段.

	//注冊步驟(parties)一般情況下可了解為線程.
	//可以通過arrive()/arriveAndAwaitAdvance()/arriveAndDeregister()推進每個已注冊步驟的完成.
	//可以在初始化Phaser時候指定,并且采用register()/bulkRegister(int parties)方法來注冊增加步驟.
	//為了讓已注冊步驟不參與下一階段的操作可采用arriveAndDeregister().
	//特殊情況下注冊步驟不可了解為線程.比如當某個線程調用兩次arrive()那麼相當于推進兩次注冊步驟.

	//Phaser.getPhase()用于擷取目前的階段.預設階段從0開始.
	//當某個階段所有的注冊步驟都完成的時候.階段值會自動增加1.
	//Phaser存在一個awaitAdvance(int phase)方法.如果形參等于Phaser.getPhase()即目前階段,那麼等待.直到phase改變的時候這個方法繼續執行.

	/*
	*以下是一些對應的解釋代碼.
	*假設一個情景:一項任務分為三個階段(phase = 3),每個階段有4個注冊步驟.
	*/

	public static void main(String[] args){
		int parties = 4;//四個步驟
		Phaser phaser = new Phaser(parties);
		Thread[] threads = new Thread[parties];
		for(int i = 0 ; i < parties; i ++){
			threads[i] = new Thread(new PhaserTest(phaser));
		}

		try{
			for(int i = 0 ; i < parties ; i ++){
				threads[i].join();
				threads[i].start();
			}
			Thread.sleep(10);
		}catch(InterruptedException e){
			e.printStackTrace();
		}

		System.out.println(phaser.isTerminated());

	}

	@Override
	public void run(){
		first();
		second();
		third();
	}

	public void first(){
		System.out.println(Thread.currentThread().getName() + ":first.");
		phaser.arriveAndAwaitAdvance();
	}

	public void second(){
		System.out.println(Thread.currentThread().getName() + ":second.");
		phaser.arriveAndAwaitAdvance();
	}

	public void third(){
		System.out.println(Thread.currentThread().getName() + ":third.");
		phaser.arriveAndDeregister();
	}

	private final Phaser phaser;

}