user165210
user165210

Reputation: 300

ExecutorService stop and waiting to another ExecutorService to finish in Java

I have two ExecutorService instances: One with 4 threads and the other, with 20 threads. I want that on a button click, Service 1 stops and waits for Service 2 to end. And afterwards, Service 1 continues to run.

I tried to do this with wait and notify but it's not working as expected:

ExecutorService 1:

    public void readFile(JTextArea textArea) {
    try {
        File file = new File(this.fm.fullPath);
        if (!file.exists()) {
            return;
        }
        BufferedReader br = new BufferedReader(new FileReader(this.fm.fullPath));

        ExecutorService executor = Executors.newFixedThreadPool(main.TOTALSTRINGS);

        String line = br.readLine();

        int i=1;
        while (line != null) {
            powThread t = new powThread("Thread" + (i+1), line, textArea);
            executor.execute(t);
            line = br.readLine();
            i++;
        }

        executor.shutdown();
        Thread t = new Thread() {
            public void run() {
                try {
                    executor.awaitTermination(Long.MAX_VALUE, TimeUnit.NANOSECONDS);
                    br.close();
                } catch (Exception e) {

                }
            }
        };
        t.start();

    } catch (IOException e) {
        e.printStackTrace();
    }
}

ExecutorService2 :

    public void generateNumStrings(JTextArea textArea) {
    StringGenerator sg = new StringGenerator();

    int[] dynamicThreads = main.calcThreadsTotal();
    int totalThreads = dynamicThreads.length;

    ExecutorService executor = Executors.newFixedThreadPool(totalThreads);

    for(int i=0; i<totalThreads; i++) {
        generateThread t = new generateThread("Thread" + (i+1), sg, dynamicThreads[i], this.fm);
        executor.execute(t);
    }

    executor.shutdown();

    Thread t = new Thread() {
        public void run() {
            try {
                textArea.setText("");
                executor.awaitTermination(Long.MAX_VALUE, TimeUnit.NANOSECONDS);
                textArea.append("File write successfully!");
            } catch (InterruptedException e) {

            }
        }
    };
    t.start();
}

Upvotes: 1

Views: 231

Answers (1)

Zim-Zam O&#39;Pootertoot
Zim-Zam O&#39;Pootertoot

Reputation: 18158

You can use an AtomicReference in the first ExecutorService to wrap the second ExecutorService or null if the second ExecutorService hasn't been instantiated, then awaitTermination if the reference is non-null. I'm assuming that readFile and generateNumStrings are in the same class, if not then you'll need to find some way to make the AtomicReference visible to generateNumStrings

private final AtomicReference<ExecutorService> ref = new AtomicReference<>(null);

private void awaitTermination() throws InterruptedException {
    ExecutorService executor = ref.get();
    if(executor != null) {
        executor.awaitTermination(1, TimeUnit.DAYS);
    }
}

public void readFile(JTextArea textArea) {
...
    while (line != null) {
        awaitTermination();
        powThread t = new powThread("Thread" + (i+1), line, textArea);
        executor.execute(t);
        line = br.readLine();
        i++;
    }
...
}

public void generateNumStrings(JTextArea textArea) {
...
    ExecutorService executor = Executors.newFixedThreadPool(totalThreads);
    ref.set(executor);
...
}

Upvotes: 2

Related Questions