0

How to use the CounDownLatch for two different threads each of them has the same runnable class?? i want FICS and fiCS_R7 to have the same runnable class FICS, but when fiCS_R3 finishes fiCS_R7 starts.

how can I do that.

Code:

    public FICSFilter(Mat bgrMat, int csRadius) {
        // TODO Auto-generated constructor stub
        this.bgrMat = bgrMat;
        this.csRadius = csRadius;

        CountDownLatch latch = new CountDownLatch(1);

        this.fiCS_R3 = new Thread(new FICS(this.bgrMat, 3), "FICS_R" + this.csRadius);
        fiCS_R3.start();

        this.fiCS_R3 = new Thread(new FICS(this.bgrMat, 7), "FICS_R" + this.csRadius);
        fiCS_R7.start();

        //How to use the CounDownLatch for two different threads each of them has the same runnable class
        }

    private class FICS implements Runnable {

    private Mat bgrMat;
    private int csRadius;

    public FICS(Mat bgrMat, int csRadius) {
        // TODO Auto-generated constructor stub
        this.bgrMat = bgrMat;
        this.csRadius = csRadius;
    }

    public void run() {
        // TODO Auto-generated method stub
        calcFICS(this.bgrMat, this.csRadius);
    }

    public static void calcFICS(Mat bgrMat, int csRadius) {
    // TODO Auto-generated method stub

    ArrayList<Mat> onOffCSActRegMatsList = null;
    ArrayList<Mat> offOnCSActRegMatsList = null;

    ArrayList<Mat> onOffCSFullMatsList = null;
    ArrayList<Mat> offOnCSFullMatsList = null;

    onOffCSActRegMatsList = new ArrayList<Mat>();
    offOnCSActRegMatsList = new ArrayList<Mat>();
isnot2bad
  • 24,105
  • 2
  • 29
  • 50
Amrmsmb
  • 1
  • 27
  • 104
  • 226
  • 1
    What's the point of using threads if you don't want them to run concurrently? – John Bollinger May 02 '15 at 15:29
  • @JohnBollinger i want them to run concurrently, but i want to use the CountDownLatch in the aforementioned situation.or in other words, when the first thread finishes the second should starts – Amrmsmb May 02 '15 at 15:30
  • 1
    Explain how the two sentences "I want them to run concurrently" and "when fiCS_R3 finishes fiCS_R7 starts" go together. – RealSkeptic May 02 '15 at 15:32
  • @RealSkeptic oh sorry...i just said concurrent because i know that countDownLatch is a concurrency technique if i am not mistaken..but in my question i want to use the countdownlatch..is it posssible – Amrmsmb May 02 '15 at 15:35
  • Using a countdown latch might be possible, but it's dumb. To run the two jobs serially, just execute their `run()` methods sequentially in the main thread. – John Bollinger May 02 '15 at 15:36
  • Yes, though useless... Please read the [CountDownLatch documentation](http://docs.oracle.com/javase/8/docs/api/java/util/concurrent/CountDownLatch.html), it includes an example. – RealSkeptic May 02 '15 at 15:36
  • Do you insist on using a `CountDownLatch`, or is any other mechanism that does what you want ok too? – isnot2bad May 02 '15 at 15:48

3 Answers3

0

Given two references r1 and r2 of type Runnable (note that r1 can also be equal to r2), it is very easy to run them sequentially, so that r1 happens-before r2:

r1.run();
r2.run(); // will start when r1 has finished

This technique is called 'sequential execution' and allows you to reuse the thread that runs r1 (the current execution thread) for running r2 afterwards, without requiring any thread synchronization mechanisms like a CountDownLatch.

isnot2bad
  • 24,105
  • 2
  • 29
  • 50
0

You could perform the job with a CountDownLatch if for some reason you are obligated to do so. The trick is that the first thread must run without waiting on the latch, then decrement its counter, whereas the second must await the latch. There are any number of ways to implement the details, but here's one:

class FICSFilter {
    Mat bgrMat;
    int csRadius;

    public FICSFilter(Mat bgrMat, int csRadius) {
        this.bgrMat = bgrMat;
        this.csRadius = csRadius;
    }

    public void doFilter() {
        CountDownLatch openLatch = new CountDownLatch(0);
        CountDownLatch latch = new CountDownLatch(1);
        Thread fiCS_R3_Thread = new Thread(
                new FICS(3, openLatch, latch), "FICS_R3");
        Thread fiCS_R7_Thread = new Thread(
                new FICS(7, latch, latch), "FICS_R7");

        fiCS_R3.start();
        fiCS_R7.start();
        fics_R7.join();
    }

    private class FICS implements Runnable {

        private Mat bgrMat;
        private int csRadius;
        private CountDownLatch startLatch;
        private CountDownLatch signalLatch;

        public FICS(int csRadius, CountDownLatch startLatch,
                CountDownLatch signalLatch) {
            this.bgrMat = FICSFilter.this.bgrMat; // for clarity only
            this.csRadius = csRadius;
            this.startLatch = startLatch;         // assumed non-null
            this.signalLatch = signalLatch;       // assumed non-null
        }

        public void run() {
            startLatch.await();

            // ... perform the calculation ...

            signalLatch.countDown();
        }
    }
}

If you just need to run the jobs sequentially, however, and a CountDownLatch was simply one idea of how that might be accomplished, then this is a far superior solution:

class FICSFilter {
    Mat bgrMat;

    public FICSFilter(Mat bgrMat) {
        this.bgrMat = bgrMat;
    }

    public void doFilter() {
        Runnable fiCS_R3 = new FICS(this.bgrMat, 3);
        Runnable fiCS_R7 = new FICS(this.bgrMat, 7);

        fiCS_R3.run();
        fiCS_R7.run();
    }

    private class FICS implements Runnable {
        // As originally written ...
    }
}

The primary purpose of a CountDownLatch is to implement checkpointing, where one wants multiple threads to all reach the same point in their work before any of them proceed further. In that case, you initialize a latch with the number of threads, and at the checkpoint each one first decrements the latch and then waits on it:

latch.countDown();
latch.await();

The construct can be applied to other tasks, such as the one you asked about, but it is more natural for some than for others. It is quite unnatural for your particular task.

John Bollinger
  • 160,171
  • 8
  • 81
  • 157
0

import java.util.ArrayList; import java.util.concurrent.CountDownLatch;

public class FICSFilter {

Mat bgrMat;
int csRadius;


public FICSFilter(Mat bgrMat, int csRadius) {
    this.bgrMat = bgrMat;
    this.csRadius = csRadius;
    //How to use the CounDownLatch for two different threads each of them has the same runnable class
}

public static void main(String args[]){

    // CountDownLatch startLatch = new CountDownLatch(1);

    CountDownLatch doneLatch = new CountDownLatch(1);

    Mat lbgrmat = new Mat();

    Thread fiCS_R3 = new Thread(new FICS(lbgrmat, 10, doneLatch));
    Thread fiCS_R7 = new Thread(new FICS(lbgrmat, 20, null));

    fiCS_R3.start();

    try {
        System.out.println("\n Going into block state in main");
        doneLatch.await();
        System.out.println("\n Out of block state in main");

    } catch (InterruptedException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
    fiCS_R7.start();
}

}

class FICS implements Runnable {

CountDownLatch doneSignal;

Mat bgrMat;
int csRadius;

public FICS(Mat bgrMat, int csRadius, CountDownLatch llatch ) {
    this.bgrMat = bgrMat;
    this.csRadius = csRadius;
    this.doneSignal = llatch;
}

public void run() {
    calcFICS(this.bgrMat, this.csRadius);

}

public void calcFICS(Mat bgrMat, int csRadius)   {
    System.out.println("\n Radius : " + csRadius + " Thread : "+ Thread.currentThread().getName());
    try {
        Thread.sleep(5000);
    } catch (InterruptedException e) {
        e.printStackTrace();
    }
    if (doneSignal != null )
        doneSignal.countDown();
}

}

The above code blocks on a latch in the main thread and only when the first thread FICS3 does its work and releases the latch, does the main thread start the next thread.

acearch
  • 343
  • 1
  • 8