A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© wnmmp 中级黑马   /  2014-8-9 23:46  /  1301 人查看  /  1 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

《张孝祥Java多线程与并发库高级应用视频教程》里面关于CyclicBarrier同步工具的应用中,当运行线程改为5个时,运行结果出现不在同一地点就出发了,谁能解释一下?
  1. package cn.itcast.heima2;

  2. import java.util.concurrent.CyclicBarrier;
  3. import java.util.concurrent.ExecutorService;
  4. import java.util.concurrent.Executors;

  5. public class CyclicBarrierTest {

  6.         public static void main(String[] args) {
  7.                 ExecutorService service = Executors.newCachedThreadPool();
  8.                 final CyclicBarrier cb = new CyclicBarrier(3);
  9.                 for (int i = 0; i < 5; i++) {
  10.                         Runnable runnable = new Runnable() {
  11.                                 public void run() {
  12.                                         try {
  13.                                                 Thread.sleep((long) (Math.random() * 1000));
  14.                                                 System.out.println("线程"
  15.                                                                 + Thread.currentThread().getName()
  16.                                                                 + "即将到达集合地点1,当前已有"
  17.                                                                 + (cb.getNumberWaiting() + 1)
  18.                                                                 + "个已经到达,"
  19.                                                                 + (cb.getNumberWaiting() == 2 ? "都到齐了,继续走啊"
  20.                                                                                 : "正在等候"));
  21.                                                 cb.await();

  22.                                                 Thread.sleep((long) (Math.random() * 1000));
  23.                                                 System.out.println("线程"
  24.                                                                 + Thread.currentThread().getName()
  25.                                                                 + "即将到达集合地点2,当前已有"
  26.                                                                 + (cb.getNumberWaiting() + 1)
  27.                                                                 + "个已经到达,"
  28.                                                                 + (cb.getNumberWaiting() == 2 ? "都到齐了,继续走啊"
  29.                                                                                 : "正在等候"));
  30.                                                 cb.await();
  31.                                                 Thread.sleep((long) (Math.random() * 1000));
  32.                                                 System.out.println("线程"
  33.                                                                 + Thread.currentThread().getName()
  34.                                                                 + "即将到达集合地点3,当前已有"
  35.                                                                 + (cb.getNumberWaiting() + 1)
  36.                                                                 + "个已经到达,"
  37.                                                                 + (cb.getNumberWaiting() == 2 ? "都到齐了,继续走啊"
  38.                                                                                 : "正在等候"));
  39.                                                 cb.await();
  40.                                         } catch (Exception e) {
  41.                                                 e.printStackTrace();
  42.                                         }
  43.                                 }
  44.                         };
  45.                         service.execute(runnable);
  46.                 }
  47.                 service.shutdown();
  48.         }
  49. }
  50. /*结果:
  51. 线程pool-1-thread-1即将到达集合地点1,当前已有1个已经到达,正在等候
  52. 线程pool-1-thread-5即将到达集合地点1,当前已有2个已经到达,正在等候
  53. 线程pool-1-thread-3即将到达集合地点1,当前已有3个已经到达,都到齐了,继续走啊
  54. 线程pool-1-thread-4即将到达集合地点1,当前已有1个已经到达,正在等候
  55. 线程pool-1-thread-2即将到达集合地点1,当前已有2个已经到达,正在等候
  56. 线程pool-1-thread-3即将到达集合地点2,当前已有3个已经到达,都到齐了,继续走啊
  57. 线程pool-1-thread-5即将到达集合地点2,当前已有1个已经到达,正在等候
  58. 线程pool-1-thread-3即将到达集合地点3,当前已有2个已经到达,正在等候
  59. 线程pool-1-thread-2即将到达集合地点2,当前已有3个已经到达,都到齐了,继续走啊
  60. 线程pool-1-thread-5即将到达集合地点3,当前已有1个已经到达,正在等候
  61. 线程pool-1-thread-1即将到达集合地点2,当前已有2个已经到达,正在等候
  62. 线程pool-1-thread-4即将到达集合地点2,当前已有3个已经到达,都到齐了,继续走啊
  63. 线程pool-1-thread-4即将到达集合地点3,当前已有1个已经到达,正在等候
  64. 线程pool-1-thread-2即将到达集合地点3,当前已有2个已经到达,正在等候
  65. 线程pool-1-thread-1即将到达集合地点3,当前已有3个已经到达,都到齐了,继续走啊*/
复制代码

1 个回复

倒序浏览
本帖最后由 yqj 于 2014-8-12 15:38 编辑

因为线程等待值为3,线程为5,每次只要满3个线程就运行,而cb.await();是同一个对象的等待方法,虽然关卡cb.await()出现的地方不同,但都视为同一关卡
                                             
线程   A     B     C      D      E
          |       |       |       |       |
关卡  CB   CB  CB       |       |  (DE没赶上,等下一趟车)   (ABC)第一次
         |       |        |       |       |
关卡  |       |        CB   CB  CB    (二缺一C搭上了DE的车,AB没搭上)   (DE)第一次,C第二次
         .....................



回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马