Creating and Managing Threads in Java
Threading in the early days of Java use to be a pain. Since Java 1.5 and the introduction of the ExecutorService, it is much easier to start up and manage them. Code that you want executed in a separate thread must be encapsulated in a class that implements Runnable. An instance of that class can then be passed to an ExecutorService that will handle its execution. Below is a trivial example but it demonstrates how to use the ExecutorService and thread pools.
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;
import org.apache.log4j.Logger;
public class ExecutorServiceExample {
public static void main (String args[]) {
final Logger logger = Logger.getLogger(ExecutorServiceExample.class);
ExecutorService threadExecutor = Executors.newFixedThreadPool( 10 );
for (int i = 0; i < 20; i++) {
threadExecutor.execute(new Runnable() {
@Override
public void run() {
try {
logger.info("This thread is going to sleep");
Thread.sleep((long)(Math.random() * 10000));
} catch (InterruptedException e) {
logger.error("Oh noes... interruptted thread?!",e);
}
}
});
}
threadExecutor.shutdown();
try {
threadExecutor.awaitTermination(5, TimeUnit.MINUTES);
logger.info("All threads done");
} catch (InterruptedException e) {
logger.error("Oh noes... interruptted thread?!",e);
}
}
}
In the example above, I created an ExecutorService that manages a pool of 10 threads. It then executes 20 anonymous classes which log an info message and sleep between 0 and 10 seconds. After that, it waits for the threads to finish executing and then logs another info message.
As you can see from the output below, the 10 threads in the pool execute one after the other. After that though, as different threads complete execution before others, they begin executing out of order due to their availability.
Output: 2011-09-13 22:07:19,511 [pool-1-thread-1] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:19,512 [pool-1-thread-3] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:19,511 [pool-1-thread-2] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:19,512 [pool-1-thread-4] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:19,512 [pool-1-thread-5] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:19,512 [pool-1-thread-6] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:19,512 [pool-1-thread-7] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:19,513 [pool-1-thread-8] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:19,513 [pool-1-thread-9] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:19,513 [pool-1-thread-10] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:19,619 [pool-1-thread-1] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:21,424 [pool-1-thread-6] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:21,815 [pool-1-thread-2] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:22,567 [pool-1-thread-10] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:23,474 [pool-1-thread-10] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:23,863 [pool-1-thread-9] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:24,473 [pool-1-thread-8] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:24,569 [pool-1-thread-7] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:25,506 [pool-1-thread-5] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:27,492 [pool-1-thread-4] INFO ExecutorServiceExample - This thread is going to sleep
2011-09-13 22:07:34,308 [main] INFO ExecutorServiceExample - All threads done