I have wrote code sample:
class Test {
public static void main(String[] args) throws InterruptedException {
ThreadPoolExecutor executorService = new ThreadPoolExecutor(0, 100,
2L, TimeUnit.SECONDS,
new LinkedBlockingQueue<Runnable>());
executorService.allowCoreThreadTimeOut(true);
CountDownLatch countDownLatch = new CountDownLatch(20);
long l = System.currentTimeMillis();
for (int i = 0; i < 20; i++) {
Thread.sleep(100);
executorService.submit(new Runnable() {
@Override
public void run() {
try {
countDownLatch.countDown();
Thread.sleep(500);
} catch (Exception e) {
System.out.println(e);
}
}
});
}
executorService.shutdown();
countDownLatch.await();
System.out.println((System.currentTimeMillis() - l) / 100);
}
}
Each 100 ms submits new task(overall task quantity - 20). Each task duration - 0.5 sec. thus 5 task can be executed in parallel and best execution time will be: 20*100+500 = 2.5 sec and pool should create 5 threads
But my experiment shows 9.6 sec.
I opened the jsvisualvm
to see how many threads pool creates and I see that only one thread was created:
please correct where my threadPooll configuration incorrect.
I guess the answer to this behavior could be rooted in:
A ThreadPoolExecutor will automatically adjust the pool size (see getPoolSize()) according to the bounds set by corePoolSize (see getCorePoolSize()) and maximumPoolSize (see getMaximumPoolSize()). When a new task is submitted in method execute(java.lang.Runnable), and fewer than corePoolSize threads are running, a new thread is created to handle the request, even if other worker threads are idle. If there are more than corePoolSize but less than maximumPoolSize threads running, a new thread will be created only if the queue is full.
( from ThreadPoolExecutor javadoc ).
Thing is: how are sleeping threads coming into this equation. My suggestion: change the corePoolSize from 0 to 10; and set the max pool size to 10, too.