How to wait for threads to complete in Java where threads are initiated using run()

Refresh

December 2018

Views

156 time

2

I am starting these threads:

          ThreadingHDFSUsage HDFSUsage=new ThreadingHDFSUsage(dcaps);  
          ThreadingRAMandContainers RAMandContainers=new ThreadingRAMandContainers(dcaps);  
          ThreadingCoreNodesHDFSUsage CoreNodesHDFSUsage=new ThreadingCoreNodesHDFSUsage(dcaps);
          ThreadingApplicationMonitoring ApplicationMonitoring= new ThreadingApplicationMonitoring(dcaps);

How should i wait for all these threads to complete before doing some other operation.

My sample thread class code for one thread operation is:

public class ThreadingHDFSUsage extends Thread {

//private PhantomJSDriver driver;

private DesiredCapabilities dcaps;

 public ThreadingHDFSUsage(DesiredCapabilities dcaps) {
    // TODO Auto-generated constructor stub
     this.dcaps = dcaps;
}

public void run(){  
     System.out.println("task HDFS Usage");  

    PhantomJSDriver driver = new PhantomJSDriver(dcaps);
    try {
        Thread.sleep(10000);
    } catch (InterruptedException e1) {
        // TODO Auto-generated catch block
        e1.printStackTrace();
    }
     System.out.println(".........HDFS Usage..........");
     String OverallHDFSUsage[] = null;
    try {
        OverallHDFSUsage = HDFSUsage.getWebData(driver,"http://1.2.3.4:8888/dfshealth.html#tab-overview","//*[@id=\"tab-overview\"]/table[2]/tbody/tr[2]/td","");
    } catch (InterruptedException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
     String OverallHDFSUsage1 = OverallHDFSUsage[0];


 }  
}

Similarly, I have relevant code for other threads.

So, how do i wait for all these 4 thread operation to complete?

3 answers

0

И других ответов являются правильными, но для полноты картины , есть еще один способ сделать то , что вы хотите с помощью Semaphore. Этот метод не будет давать результаты , отличные от любых других ответов, но может быть быстрее , если любому из ваших ниток нужно сделать что - то дорогое после получения результатов вы хотите получены, до возвращения. Внутри каждого из потоков, звоните , s.release()как только все соответствующая работа закончена. Ваш контроллер поток может выглядеть следующим образом ...

Semaphore s = new Semaphore(0);
//start all four of your threads here and pass 's' to each
s.acquire(4);

... и ваши рабочие потоки могли бы выглядеть следующим образом:

@Override
public void run(){
    //compute results
    s.release(1);
    //do expensive cleanup and return
}
2

Просто присоединиться () их снова:

HDFSUsage.join();  
RAMandContainers.join();
CoreNodesHDFSUsage.join();
ApplicationMonitoring.join();

Каждый присоединиться () ожидает конкретный поток, чтобы закончить.

0

Там же CompletionServiceв JDK concurrentпакете. Для того, чтобы использовать его, вы можете переключаться с явным Threadsдля задач, представленных в виде экземпляров Callable<ResultType>или Runnable. В то время как код может выглядеть немного более сложным, это очень удобно, когда вы привыкли к нему:

import java.util.concurrent.*;

class Test {

    public static void main(String[] args) throws InterruptedException, ExecutionException {
        CompletionService<String> completionService = new ExecutorCompletionService<>(Executors.newCachedThreadPool());
        completionService.submit(() -> {
            Thread.sleep(5000);
            return "sleeped for 5000 millis";
        });
        completionService.submit(() -> {
            Thread.sleep(1000);
            return "sleeped for 1000 millis";
        });
        // etc
        System.out.println("Completed: " + completionService.take().get());
        System.out.println("Completed: " + completionService.take().get());
    }

}