Reputation: 213
Can same thread be used to execute many tasks one by one without destroying and re-creating thread?
public class SimpleThreadPool {
public static void main(String[] args) {
ExecutorService executorService = Executors.newFixedThreadPool(5);
for (int i = 0; i < 10; i++) {
Runnable worker = new WorkerThread("" + i);
executorService.execute(worker); // How many threads are created?
}
executorService.shutdown();
while (!executorService.isTerminated()) {
}
System.out.println("All threads Executed");
}
}
Upvotes: 2
Views: 676
Reputation: 45806
Yes, the same Thread
can be used to run more than one task. This is what ExecutorService
does: it maintains a thread pool for reusing threads rather than creating new ones for each task. A rough idea of how this is done is below:
import java.util.Objects;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.Executor;
import java.util.concurrent.LinkedBlockingQueue;
public class MyExecutor implements Executor {
private final BlockingQueue<Runnable> queue = new LinkedBlockingQueue<>();
private final Thread thread = new Thread(() -> {
try {
while (!Thread.interrupted()) {
queue.take().run();
}
} catch (Exception ex) {
ex.printStackTrace();
}
}, "my-executor-thread");
@Override
public void execute(Runnable command) {
Objects.requireNonNull(command);
queue.add(command);
synchronized (thread) {
if (thread.getState() == Thread.State.NEW) {
thread.start();
}
}
}
}
Note that the real implementations are much more complicated than this. For instance, I did not add a way to create a new Thread
if some error causes the current one to die. I also don't protect the Thread
from possible exceptions thrown from the Runnable
.
As you can see, the Runnable
used with the Thread
(via new Thread(Runnable)
) simply waits for tasks to be put into a BlockingQueue
. When a new task is added to the BlockingQueue
the Thread
takes it and executes run()
. This is how a single Thread
can run more than one task without being destroyed and another one taking its place.
Note this means if all the pool's threads (or, in this case, single thread) are busy with a task any queued tasks will have to wait.
Upvotes: 4
Reputation: 18774
ExecutorService executorService = Executors.newFixedThreadPool(5);
this will create only 5 threads in the Executor
.
for (int i = 0; i < 10; i++) {
Runnable worker = new WorkerThread("" + i);
executorService.execute(worker); // How many threads are created?
}
This creates 10 tasks that are submitted to the executor service for execution. And the ExecutorService will use the fixed 5 threads to execute those 10 tasks. So Yes, you will have one thread doing multiple tasks without being re-created.
Upvotes: 0