Reputation: 302
I am playing around multithreading to understand it properly. So I was trying to test how "number of threads being created" can impact the total runtime of a given task.
class Worker implements Runnable {
private int id;
public Worker(int id) {
this.id = id;
}
@Override
public void run() {
System.out.println("Starting thread ->" + Thread.currentThread().getName() + " with ID: " + id);
System.out.println("Finishing thread ->" + Thread.currentThread().getName() + " with ID: " + id);
}
}
public class App {
public static void main(String[] args) throws InterruptedException {
App app = new App();
ExecutorService threadPool;
Map<Integer, Long> performanceMetric = new HashMap<>();
for (int j = 3; j > 0; j -= 1) {
long begin = System.currentTimeMillis();
So here I am creating highest number of threads by assigning a high value on the loop. Am simply using the value of "j" from the loop and assigning it to the Executor.
threadPool = Executors.newFixedThreadPool(j);
System.out.println("\nTotal threads created: " + j);
app.performService(threadPool);
threadPool.shutdown();
Ensuring that the executor (threadpool) is shutdown first before calculating the total time taken.
threadPool.awaitTermination(1, TimeUnit.SECONDS);
Here am calculating the total time taken for completing the task. The total time wont be calculated unless all the tasks are complete.
long totalTime = (System.currentTimeMillis() - begin);
System.out.println("Is the ThreadPool shutdown: " + (threadPool.isTerminated() ? "Yes" : "No"));
performanceMetric.put(j, totalTime);
System.out.println("\nTotal time elapsed when using " + j + " threads is " + totalTime + " milliseconds");
}
Set<Integer> keySet = performanceMetric.keySet();
for (int key : keySet) {
System.out.println("\nSUMMARY\n\nTotal time elapsed when using " + key + " threads is "
+ performanceMetric.get(key) + " milliseconds");
}
}
public void performService(ExecutorService threadPool) {
for (int i = 0; i < 5; i++) {
threadPool.submit(new Worker(i));
}
}
}
The output for the above program is below
Begin output
Total threads created: 3
Starting thread ---pool-1-thread-1 with ID: 0
Starting thread ---pool-1-thread-3 with ID: 2
Starting thread ---pool-1-thread-2 with ID: 1
Finishing thread ---pool-1-thread-3 with ID: 2
Finishing thread ---pool-1-thread-1 with ID: 0
Finishing thread ---pool-1-thread-2 with ID: 1
Starting thread ---pool-1-thread-3 with ID: 3
Starting thread ---pool-1-thread-2 with ID: 4
Finishing thread ---pool-1-thread-3 with ID: 3
Finishing thread ---pool-1-thread-2 with ID: 4
Is the ThreadPool shutdown: Yes
Total time elapsed when using 3 threads is 4 milliseconds
Total threads created: 2
Starting thread ---pool-2-thread-1 with ID: 0
Finishing thread ---pool-2-thread-1 with ID: 0
Starting thread ---pool-2-thread-1 with ID: 2
Finishing thread ---pool-2-thread-1 with ID: 2
Starting thread ---pool-2-thread-2 with ID: 1
Finishing thread ---pool-2-thread-2 with ID: 1
Starting thread ---pool-2-thread-1 with ID: 3
Finishing thread ---pool-2-thread-1 with ID: 3
Starting thread ---pool-2-thread-2 with ID: 4
Finishing thread ---pool-2-thread-2 with ID: 4
Is the ThreadPool shutdown: Yes
Total time elapsed when using 2 threads is 0 milliseconds
Total threads created: 1
Starting thread ---pool-3-thread-1 with ID: 0
Finishing thread ---pool-3-thread-1 with ID: 0
Starting thread ---pool-3-thread-1 with ID: 1
Finishing thread ---pool-3-thread-1 with ID: 1
Starting thread ---pool-3-thread-1 with ID: 2
Finishing thread ---pool-3-thread-1 with ID: 2
Starting thread ---pool-3-thread-1 with ID: 3
Finishing thread ---pool-3-thread-1 with ID: 3
Starting thread ---pool-3-thread-1 with ID: 4
Finishing thread ---pool-3-thread-1 with ID: 4
Is the ThreadPool shutdown: Yes
Total time elapsed when using 1 threads is 0 milliseconds
Total time elapsed when using 1 threads is 0 milliseconds
Total time elapsed when using 2 threads is 0 milliseconds
Total time elapsed when using 3 threads is 4 milliseconds
end output
I am surprised how one or two threads performed faster compared to three threads. Can someone please explain.
Upvotes: 0
Views: 35
Reputation: 269687
You aren't doing a constant amount of work in each trial, divided by a varying number of threads. You are simply creating a varying number of threads. The more threads you have to create, start, and monitor, the longer it will take.
That's your multi-threading overhead; it's only worthwhile when your work load will benefit from parallelization. In this example, it doesn't.
Upvotes: 1