并发同步器 CountDownLatch的用法
程序员文章站
2022-06-06 21:35:23
...
CountDownlatch 一个同步辅助类,在完成一组正在其他线程中执行的操作之前,它允许一个或多个线程一直等待,此场景适用在完成所有任务之后才能继续下面的任务的场景 比如下面田径运动员 只有运动员全部跑完比赛才能 进行下面的成绩统计
接下来是田径运动员
下面是成绩统计类
最终运行结果
import java.util.Arrays; import java.util.concurrent.CountDownLatch; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; /** * * CountDownLatch类是一个同步计数器,构造时传入int参数,该参数就是计数器的初始值, * 每调用一次countDown()方法,计数器减1,计数器大于0 时,await()方法会阻塞程序继续执行 * */ public class CountDownLatchTest1 { private final static int NUM=6;//6个运动员 public static void main(String[] args) { CountDownLatch begin=new CountDownLatch(1); CountDownLatch end =new CountDownLatch(NUM); Player[] players=new Player[NUM]; for(int i=0;i<NUM;i++) players[i]=new Player("aa"+(i+1), begin, end); StatisticScore t=new StatisticScore(players); ExecutorService excutorService=Executors.newFixedThreadPool(NUM); for(Player p:players) excutorService.execute(p); // 比赛开始 begin.countDown(); try { end.await(); } catch (InterruptedException e) { e.printStackTrace(); } excutorService.shutdown(); //开始统计成绩 t.start(); } }
接下来是田径运动员
/** * 田径运动员 * */ class Player extends Thread implements Comparable<Player>{ //成绩 private int score; //名字 private String name; //开始同步计时器 private CountDownLatch begin; //结束同步计时器 private CountDownLatch end; public Player(String name,CountDownLatch begin,CountDownLatch end) { this.name=name; this.begin=begin; this.end=end; } @Override public void run() { // try { //等待口令准备开始 begin.await(); } catch (InterruptedException e) { e.printStackTrace(); } try { //开始运动 System.out.println("运动员["+name+"] 开始跑"); int n=(int) (Math.random()*50); Thread.sleep(n); //运动结束 //成绩为 score=n; System.out.println("运动员["+name+"] 跑完,成绩:"+score+"s"); } catch (InterruptedException e) { e.printStackTrace(); } end.countDown(); } @Override public int compareTo(Player o) { return score-o.getScore(); } public int getScore() { return score; } public String getPlayerName(){ return name; } }
下面是成绩统计类
/** * 成绩统计 */ class StatisticScore extends Thread{ Player[] players; public StatisticScore(Player[] players) { this.players=players; } @Override public void run() { System.out.println("成绩统计排行榜如下:"); Arrays.sort(players);//成绩排名 for(int i=0;i<players.length;i++){ System.out.println("运动员["+players[i].getPlayerName()+"] 第"+(i+1)+"名 成绩:"+players[i].getScore()+"s"); } } }
最终运行结果
运动员[aa2] 开始跑 运动员[aa4] 开始跑 运动员[aa5] 开始跑 运动员[aa1] 开始跑 运动员[aa3] 开始跑 运动员[aa6] 开始跑 运动员[aa6] 跑完,成绩:3s 运动员[aa5] 跑完,成绩:5s 运动员[aa4] 跑完,成绩:14s 运动员[aa1] 跑完,成绩:31s 运动员[aa2] 跑完,成绩:33s 运动员[aa3] 跑完,成绩:49s 成绩统计排行榜如下: 运动员[aa6] 第1名 成绩:3s 运动员[aa5] 第2名 成绩:5s 运动员[aa4] 第3名 成绩:14s 运动员[aa1] 第4名 成绩:31s 运动员[aa2] 第5名 成绩:33s 运动员[aa3] 第6名 成绩:49s