newFixedThreadPool.setCorePoolSize()不使用线程,创建新的theads。
说明: 我为大小2创建了一个newFixedThreadPool,如果这个池的两个线程都忙,我使用setCorePoolSize()向这个池添加两个线程。在这个过程中,它似乎没有重用线程,或者可能正在终止一些线程并创建新的,我将用代码解释。
public class IncreasePoolSize
{
static ExecutorService service = null;
public static void main(String[] args) throws JMSException, InterruptedException
{
int NoOfth = 2;
int noOfTimesToInc = 0;
System.out.println("Start");
service = Executors.newFixedThreadPool(NoOfth);
for (;;)
{
if ( ((ThreadPoolExecutor)service).getActiveCount() >= NoOfth )
{
if (noOfTimesToInc < 1)
{
System.out.println("Increased Threads-" + (noOfTimesToInc + 1) + " time(s)");
NoOfth += 2;
System.out.println("NoOfTh-" + NoOfth);
((ThreadPoolExecutor)service).setCorePoolSize(NoOfth);
System.out.println("Total no of theads after increasing-" + ((ThreadPoolExecutor)service).getCorePoolSize());
noOfTimesToInc++;
}
}
else if ( ((ThreadPoolExecutor)service).getActiveCount() <= NoOfth)
{
service.execute(new ConcreteThread());
}
}
}
}
class ConcreteThread implements Runnable
{
public void run()
{
try
{
System.out.println("Thread No-" + Thread.currentThread().getId());
Thread.sleep(5000);
System.out.println("Thread No-" + Thread.currentThread().getId() + " finished");
}
catch(Exception e)
{
e.printStackTrace();
}
}
}
在输出中看到一旦11号线和12号线开始工作,我将数字增加2,所以线程13和14开始工作,但在那之后,我总是创建新线程而不是使用线程11和12重用第13和14行。
Start
Thread No-11
Thread No-12
Increased Threads-1 time(s)
NoOfTh-4
Total no of theads after increasing-4
Thread No-13
Thread No-14
Thread No-11 finished
Thread No-12 finished
Thread No-13 finished
Thread No-14 finished
Thread No-15
Thread No-16
Thread No-13
Thread No-14
Thread No-15 finished
Thread No-16 finished
Thread No-13 finished
Thread No-14 finished
Thread No-17
Thread No-18
Thread No-13
Thread No-14
Thread No-17 finished
Thread No-18 finished
Thread No-13 finished
Thread No-14 finished
Thread No-19
Thread No-20
Thread No-13
Thread No-14
Thread No-19 finished
Thread No-20 finished
Thread No-13 finished
Thread No-14 finished
Thread No-21
Thread No-22
Thread No-13
Thread No-14
Thread No-21 finished
Thread No-22 finished
Thread No-13 finished
Thread No-14 finished
Thread No-23
Thread No-24
Thread No-13
Thread No-14
答案 0 :(得分:5)
您的代码的一个问题是您设置了核心池大小,但没有设置最大池大小。 newFixedThreadPool
使用相同数量的核心和最大池大小,并且您稍微违反了该合同。
如果你添加:
service.setMaximumPoolSize(NoOfth);
设置核心池大小后,将按预期重复使用相同的4个线程。
注意:这实际上是a reported bug
ThreadPoolExecutor和setMaximumPoolSize
的构造函数抛出IllegalArgumentException corePoolSize > maximumPoolSize
,但setCorePoolSize
没有。{/ p>
答案 1 :(得分:2)
根据Executors.newFixedThreadPool
:
创建一个线程池,该线程池重用在共享无界队列中运行的固定数量的线程。在任何时候,最多nThreads线程将是活动处理任务
因此,它不一定是创建新线程,只是使用shared unbounded queue
中的不同线程。
固定线程池给你的不是它总是使用完全相同的线程对象,而是那个执行器中工作任务的活动线程数永远不会超过池的限制。
答案 2 :(得分:0)
如果我们去查看正在运行的实际代码,我们可以看到发生了什么。在线程池中,工作由运行此方法的工作线程完成(taken from here)
final void runWorker(Worker w) {
Runnable task = w.firstTask;
w.firstTask = null;
boolean completedAbruptly = true;
try {
while (task != null || (task = getTask()) != null) {
w.lock();
clearInterruptsForTaskRun();
try {
beforeExecute(w.thread, task);
Throwable thrown = null;
try {
task.run();
} catch (RuntimeException x) {
thrown = x; throw x;
} catch (Error x) {
thrown = x; throw x;
} catch (Throwable x) {
thrown = x; throw new Error(x);
} finally {
afterExecute(task, thrown);
}
} finally {
task = null;
w.completedTasks++;
w.unlock();
}
}
completedAbruptly = false;
} finally {
processWorkerExit(w, completedAbruptly);
}
}
正如您所看到的,这将在有任务运行的同时继续运行任务。但是,如果一个Worker用完了任务,它就会死掉,如果以后安排了更多的任务,就会创建一个新的Worker(线程)。