将CycleBarrier用于具有不同线程数的两个对象

时间:2017-09-19 15:06:09

标签: java multithreading cyclicbarrier

我手头有以下任务:

想象一下,有4个开发人员为IT解决方案实现功能,2个测试人员验证他们的工作。 项目经理为这个项目制定了一个(有争议的)战略: 在所有开发人员完成工作之前,他不希望测试人员开始验证此应用程序。 此外,他不希望开发人员在所有测试人员完成工作之前开始修复报告的缺陷(更改应用程序)。 要协调这些任务,请使用CyclicBarrier类。

经过一些研究和教程后,我设法编译以下代码,为每个CycleBarrier使用2个线程:

    public static void main(String[] args) {
    Runnable barrier1Action = new Runnable() {
        public void run() {
            System.out.println("Developers start working -> Testers start working");
        }
    };
    Runnable barrier2Action = new Runnable() {
        public void run() {
            System.out.println("Testers finish working -> Developers start fixing defects");
        }
    };

    CyclicBarrier barrier1 = new CyclicBarrier(2, barrier1Action);
    CyclicBarrier barrier2 = new CyclicBarrier(2, barrier2Action);


    CyclicBarrierRunnable barrierRunnable1 = new CyclicBarrierRunnable(barrier1, barrier2);

    CyclicBarrierRunnable barrierRunnable2 = new CyclicBarrierRunnable(barrier1, barrier2);


    new Thread(barrierRunnable1).start();
    new Thread(barrierRunnable2).start();

和CyclicBarrierRunnable类:

public class CyclicBarrierRunnable implements Runnable {

    CyclicBarrier barrier1 = null;
    CyclicBarrier barrier2 = null;

    public CyclicBarrierRunnable(CyclicBarrier barrier1, CyclicBarrier barrier2) {

        this.barrier1 = barrier1;
        this.barrier2 = barrier2;
    }

    public void run() {
        try {

            Thread.sleep(1000);
            System.out.println(Thread.currentThread().getName() + " waiting at barrier 1");
            this.barrier1.await();

            Thread.sleep(1000);
            System.out.println(Thread.currentThread().getName() + " waiting at barrier 2");
            this.barrier2.await();

            System.out.println(Thread.currentThread().getName() + " done!");

        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (BrokenBarrierException e) {
            e.printStackTrace();
        }
    }
}

我的问题是,如果第一个CyclicBarrier有4个派对而不是2个,我怎么能让应用程序运行。如果我尝试用CyclicBarrier barrier1 = new CyclicBarrier(4, barrier1Action); CyclicBarrier barrier2 = new CyclicBarrier(2, barrier2Action);运行它只有前2个线程将启动

1 个答案:

答案 0 :(得分:1)

首先,设计似乎有问题,因为开发人员和测试人员的操作不同,最好创建一个实现Runnable的两个类,而不是使用CountDownLatch来代替CyclicBarrier。 基于您的要求的示例:

import java.util.concurrent.CountDownLatch;

public class DevTest {

    static class Developer implements Runnable {

        CountDownLatch waitingForDeveloper=null;
        CountDownLatch waitingForTester   =null;

        public Developer(CountDownLatch waitingForDeveloper,CountDownLatch waitingForTester) {
            this.waitingForDeveloper=waitingForDeveloper;
            this.waitingForTester=waitingForTester;

        }
        @Override
        public void run(){

            System.out.println("Dev "+Thread.currentThread().getName()+" has completed the task");
            waitingForDeveloper.countDown();
            try{
                waitingForTester.await();
            }catch(InterruptedException ex){}
            System.out.println("Dev "+Thread.currentThread().getName()+" is Working on the bug raised by testers.");


        }
    }

    static class Tester implements Runnable {

        CountDownLatch waitingForDeveloper=null;
        CountDownLatch waitingForTester   =null;

        public Tester(CountDownLatch waitingForDeveloper,CountDownLatch waitingForTester) {
            this.waitingForDeveloper=waitingForDeveloper;
            this.waitingForTester=waitingForTester;

        }
        @Override
        public void run(){

            try{
                waitingForDeveloper.await();
            }catch(InterruptedException ex){}

            System.out.println("Tester "+Thread.currentThread().getName()+" has completed testing.");
            waitingForTester.countDown();

        }
    }
    public static void main(String[] args) {

        int noOFdevelopers=7;
        int noOFTesters=4;
        CountDownLatch waitingForDeveloper=new CountDownLatch(noOFdevelopers);
        CountDownLatch waitingForTester   =new CountDownLatch(noOFTesters);

        Developer developer=new Developer(waitingForDeveloper, waitingForTester);
        Tester    tester=new Tester(waitingForDeveloper, waitingForTester);

        for(int i=1;i<=noOFTesters;i++){
            new Thread(tester,""+i).start();
        }       
        for(int i=1;i<=noOFdevelopers;i++){
            new Thread(developer,""+i).start();
        }


    }
}

一旦你理解了这个片段,就可以尝试自己的问题解决方法

希望有所帮助!!!