Constructor: |
public ThreadPoolExecutor(int corePoolSize,
int maximumPoolSize,
long keepAliveTime,
TimeUnit unit,
BlockingQueue<Runnable> workQueue) {
this(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue,
Executors.defaultThreadFactory(), defaultHandler);
}
Creates a new ThreadPoolExecutor with the given
initial parameters and default thread factory and handler. It
may be more convenient to use one of the Executors
factory methods instead of this general purpose constructor. Parameters:
corePoolSize - the number of threads to keep in the
pool, even if they are idle.
maximumPoolSize - the maximum number of threads to allow in the
pool.
keepAliveTime - when the number of threads is greater than
the core, this is the maximum time that excess idle threads
will wait for new tasks before terminating.
unit - the time unit for the keepAliveTime
argument.
workQueue - the queue to use for holding tasks before they
are executed. This queue will hold only the Runnable
tasks submitted by the execute method.
Throws:
IllegalArgumentException - if corePoolSize, or
keepAliveTime less than zero, or if maximumPoolSize less than or
equal to zero, or if corePoolSize greater than maximumPoolSize.
NullPointerException - if workQueue is null
|
public ThreadPoolExecutor(int corePoolSize,
int maximumPoolSize,
long keepAliveTime,
TimeUnit unit,
BlockingQueue<Runnable> workQueue,
ThreadFactory threadFactory) {
this(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue,
threadFactory, defaultHandler);
}
Creates a new ThreadPoolExecutor with the given initial
parameters. Parameters:
corePoolSize - the number of threads to keep in the
pool, even if they are idle.
maximumPoolSize - the maximum number of threads to allow in the
pool.
keepAliveTime - when the number of threads is greater than
the core, this is the maximum time that excess idle threads
will wait for new tasks before terminating.
unit - the time unit for the keepAliveTime
argument.
workQueue - the queue to use for holding tasks before they
are executed. This queue will hold only the Runnable
tasks submitted by the execute method.
threadFactory - the factory to use when the executor
creates a new thread.
Throws:
IllegalArgumentException - if corePoolSize, or
keepAliveTime less than zero, or if maximumPoolSize less than or
equal to zero, or if corePoolSize greater than maximumPoolSize.
NullPointerException - if workQueue
or threadFactory are null.
|
public ThreadPoolExecutor(int corePoolSize,
int maximumPoolSize,
long keepAliveTime,
TimeUnit unit,
BlockingQueue<Runnable> workQueue,
RejectedExecutionHandler handler) {
this(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue,
Executors.defaultThreadFactory(), handler);
}
Creates a new ThreadPoolExecutor with the given initial
parameters. Parameters:
corePoolSize - the number of threads to keep in the
pool, even if they are idle.
maximumPoolSize - the maximum number of threads to allow in the
pool.
keepAliveTime - when the number of threads is greater than
the core, this is the maximum time that excess idle threads
will wait for new tasks before terminating.
unit - the time unit for the keepAliveTime
argument.
workQueue - the queue to use for holding tasks before they
are executed. This queue will hold only the Runnable
tasks submitted by the execute method.
handler - the handler to use when execution is blocked
because the thread bounds and queue capacities are reached.
Throws:
IllegalArgumentException - if corePoolSize, or
keepAliveTime less than zero, or if maximumPoolSize less than or
equal to zero, or if corePoolSize greater than maximumPoolSize.
NullPointerException - if workQueue
or handler are null.
|
public ThreadPoolExecutor(int corePoolSize,
int maximumPoolSize,
long keepAliveTime,
TimeUnit unit,
BlockingQueue<Runnable> workQueue,
ThreadFactory threadFactory,
RejectedExecutionHandler handler) {
if (corePoolSize < 0 ||
maximumPoolSize < = 0 ||
maximumPoolSize < corePoolSize ||
keepAliveTime < 0)
throw new IllegalArgumentException();
if (workQueue == null || threadFactory == null || handler == null)
throw new NullPointerException();
this.corePoolSize = corePoolSize;
this.maximumPoolSize = maximumPoolSize;
this.workQueue = workQueue;
this.keepAliveTime = unit.toNanos(keepAliveTime);
this.threadFactory = threadFactory;
this.handler = handler;
}
Creates a new ThreadPoolExecutor with the given initial
parameters. Parameters:
corePoolSize - the number of threads to keep in the
pool, even if they are idle.
maximumPoolSize - the maximum number of threads to allow in the
pool.
keepAliveTime - when the number of threads is greater than
the core, this is the maximum time that excess idle threads
will wait for new tasks before terminating.
unit - the time unit for the keepAliveTime
argument.
workQueue - the queue to use for holding tasks before they
are executed. This queue will hold only the Runnable
tasks submitted by the execute method.
threadFactory - the factory to use when the executor
creates a new thread.
handler - the handler to use when execution is blocked
because the thread bounds and queue capacities are reached.
Throws:
IllegalArgumentException - if corePoolSize, or
keepAliveTime less than zero, or if maximumPoolSize less than or
equal to zero, or if corePoolSize greater than maximumPoolSize.
NullPointerException - if workQueue
or threadFactory or handler are null.
|
Method from org.apache.geronimo.concurrent.harmony.ThreadPoolExecutor Detail: |
protected void afterExecute(Runnable r,
Throwable t) {
}
Method invoked upon completion of execution of the given
Runnable. This method is invoked by the thread that executed
the task. If non-null, the Throwable is the uncaught exception
that caused execution to terminate abruptly. Note: To properly
nest multiple overridings, subclasses should generally invoke
super.afterExecute at the beginning of this method. |
public boolean awaitTermination(long timeout,
TimeUnit unit) throws InterruptedException {
long nanos = unit.toNanos(timeout);
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
for (;;) {
if (runState == TERMINATED)
return true;
if (nanos < = 0)
return false;
nanos = termination.awaitNanos(nanos);
}
} finally {
mainLock.unlock();
}
}
|
protected void beforeExecute(Thread t,
Runnable r) {
}
Method invoked prior to executing the given Runnable in the
given thread. This method is invoked by thread t that
will execute task r, and may be used to re-initialize
ThreadLocals, or to perform logging. Note: To properly nest
multiple overridings, subclasses should generally invoke
super.beforeExecute at the end of this method. |
public void execute(Runnable command) {
if (command == null)
throw new NullPointerException();
for (;;) {
if (runState != RUNNING) {
reject(command);
return;
}
if (poolSize < corePoolSize && addIfUnderCorePoolSize(command))
return;
if (workQueue.offer(command))
return;
Runnable r = addIfUnderMaximumPoolSize(command);
if (r == command)
return;
if (r == null) {
reject(command);
return;
}
// else retry
}
}
Executes the given task sometime in the future. The task
may execute in a new thread or in an existing pooled thread.
If the task cannot be submitted for execution, either because this
executor has been shutdown or because its capacity has been reached,
the task is handled by the current RejectedExecutionHandler. |
protected void finalize() {
shutdown();
}
Invokes shutdown when this executor is no longer
referenced. |
public int getActiveCount() {
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
int n = 0;
for (Worker w : workers) {
if (w.isActive())
++n;
}
return n;
} finally {
mainLock.unlock();
}
}
Returns the approximate number of threads that are actively
executing tasks. |
public long getCompletedTaskCount() {
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
long n = completedTaskCount;
for (Worker w : workers)
n += w.completedTasks;
return n;
} finally {
mainLock.unlock();
}
}
Returns the approximate total number of tasks that have
completed execution. Because the states of tasks and threads
may change dynamically during computation, the returned value
is only an approximation, but one that does not ever decrease
across successive calls. |
public int getCorePoolSize() {
return corePoolSize;
}
Returns the core number of threads. |
public long getKeepAliveTime(TimeUnit unit) {
return unit.convert(keepAliveTime, TimeUnit.NANOSECONDS);
}
Returns the thread keep-alive time, which is the amount of time
which threads in excess of the core pool size may remain
idle before being terminated. |
public int getLargestPoolSize() {
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
return largestPoolSize;
} finally {
mainLock.unlock();
}
}
Returns the largest number of threads that have ever
simultaneously been in the pool. |
public int getMaximumPoolSize() {
return maximumPoolSize;
}
Returns the maximum allowed number of threads. |
public int getPoolSize() {
return poolSize;
}
Returns the current number of threads in the pool. |
public BlockingQueue<Runnable> getQueue() {
return workQueue;
}
Returns the task queue used by this executor. Access to the
task queue is intended primarily for debugging and monitoring.
This queue may be in active use. Retrieving the task queue
does not prevent queued tasks from executing. |
public RejectedExecutionHandler getRejectedExecutionHandler() {
return handler;
}
Returns the current handler for unexecutable tasks. |
Runnable getTask() throws InterruptedException {
for (;;) {
switch(runState) {
case RUNNING: {
if (poolSize < = corePoolSize) // untimed wait if core
return workQueue.take();
long timeout = keepAliveTime;
if (timeout < = 0) // die immediately for 0 timeout
return null;
Runnable r = workQueue.poll(timeout, TimeUnit.NANOSECONDS);
if (r != null)
return r;
if (poolSize > corePoolSize) // timed out
return null;
// else, after timeout, pool shrank so shouldn't die, so retry
break;
}
case SHUTDOWN: {
// Help drain queue
Runnable r = workQueue.poll();
if (r != null)
return r;
// Check if can terminate
if (workQueue.isEmpty()) {
interruptIdleWorkers();
return null;
}
// There could still be delayed tasks in queue.
// Wait for one, re-checking state upon interruption
try {
return workQueue.take();
} catch(InterruptedException ignore) {}
break;
}
case STOP:
return null;
default:
assert false;
}
}
}
Get the next task for a worker thread to run. |
public long getTaskCount() {
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
long n = completedTaskCount;
for (Worker w : workers) {
n += w.completedTasks;
if (w.isActive())
++n;
}
return n + workQueue.size();
} finally {
mainLock.unlock();
}
}
Returns the approximate total number of tasks that have been
scheduled for execution. Because the states of tasks and
threads may change dynamically during computation, the returned
value is only an approximation, but one that does not ever
decrease across successive calls. |
public ThreadFactory getThreadFactory() {
return threadFactory;
}
Returns the thread factory used to create new threads. |
protected void interruptIdleWorkers() {
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
for (Worker w : workers)
w.interruptIfIdle();
} finally {
mainLock.unlock();
}
}
Wake up all threads that might be waiting for tasks. |
public boolean isShutdown() {
return runState != RUNNING;
}
|
public boolean isTerminated() {
return runState == TERMINATED;
}
|
public boolean isTerminating() {
return runState == STOP;
}
Returns true if this executor is in the process of terminating
after shutdown or shutdownNow but has not
completely terminated. This method may be useful for
debugging. A return of true reported a sufficient
period after shutdown may indicate that submitted tasks have
ignored or suppressed interruption, causing this executor not
to properly terminate. |
public int prestartAllCoreThreads() {
int n = 0;
while (addIfUnderCorePoolSize(null))
++n;
return n;
}
Starts all core threads, causing them to idly wait for work. This
overrides the default policy of starting core threads only when
new tasks are executed. |
public boolean prestartCoreThread() {
return addIfUnderCorePoolSize(null);
}
Starts a core thread, causing it to idly wait for work. This
overrides the default policy of starting core threads only when
new tasks are executed. This method will return false
if all core threads have already been started. |
public void purge() {
// Fail if we encounter interference during traversal
try {
Iterator< Runnable > it = getQueue().iterator();
while (it.hasNext()) {
Runnable r = it.next();
if (r instanceof Future< ? >) {
Future< ? > c = (Future< ? >)r;
if (c.isCancelled())
it.remove();
}
}
}
catch(ConcurrentModificationException ex) {
return;
}
}
Tries to remove from the work queue all Future
tasks that have been cancelled. This method can be useful as a
storage reclamation operation, that has no other impact on
functionality. Cancelled tasks are never executed, but may
accumulate in work queues until worker threads can actively
remove them. Invoking this method instead tries to remove them now.
However, this method may fail to remove tasks in
the presence of interference by other threads. |
protected void reject(Runnable command) {
handler.rejectedExecution(command, this);
}
Invoke the rejected execution handler for the given command. |
public boolean remove(Runnable task) {
return getQueue().remove(task);
}
Removes this task from the executor's internal queue if it is
present, thus causing it not to be run if it has not already
started.
This method may be useful as one part of a cancellation
scheme. It may fail to remove tasks that have been converted
into other forms before being placed on the internal queue. For
example, a task entered using submit might be
converted into a form that maintains Future status.
However, in such cases, method ThreadPoolExecutor#purge
may be used to remove those Futures that have been cancelled. |
public void setCorePoolSize(int corePoolSize) {
if (corePoolSize < 0)
throw new IllegalArgumentException();
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
int extra = this.corePoolSize - corePoolSize;
this.corePoolSize = corePoolSize;
if (extra < 0) {
Runnable r;
while (extra++ < 0 && poolSize < corePoolSize &&
(r = workQueue.poll()) != null)
addThread(r).start();
}
else if (extra > 0 && poolSize > corePoolSize) {
Iterator< Worker > it = workers.iterator();
while (it.hasNext() &&
extra-- > 0 &&
poolSize > corePoolSize &&
workQueue.remainingCapacity() == 0)
it.next().interruptIfIdle();
}
} finally {
mainLock.unlock();
}
}
Sets the core number of threads. This overrides any value set
in the constructor. If the new value is smaller than the
current value, excess existing threads will be terminated when
they next become idle. If larger, new threads will, if needed,
be started to execute any queued tasks. |
public void setKeepAliveTime(long time,
TimeUnit unit) {
if (time < 0)
throw new IllegalArgumentException();
this.keepAliveTime = unit.toNanos(time);
}
Sets the time limit for which threads may remain idle before
being terminated. If there are more than the core number of
threads currently in the pool, after waiting this amount of
time without processing a task, excess threads will be
terminated. This overrides any value set in the constructor. |
public void setMaximumPoolSize(int maximumPoolSize) {
if (maximumPoolSize < = 0 || maximumPoolSize < corePoolSize)
throw new IllegalArgumentException();
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
int extra = this.maximumPoolSize - maximumPoolSize;
this.maximumPoolSize = maximumPoolSize;
if (extra > 0 && poolSize > maximumPoolSize) {
Iterator< Worker > it = workers.iterator();
while (it.hasNext() &&
extra > 0 &&
poolSize > maximumPoolSize) {
it.next().interruptIfIdle();
--extra;
}
}
} finally {
mainLock.unlock();
}
}
Sets the maximum allowed number of threads. This overrides any
value set in the constructor. If the new value is smaller than
the current value, excess existing threads will be
terminated when they next become idle. |
public void setRejectedExecutionHandler(RejectedExecutionHandler handler) {
if (handler == null)
throw new NullPointerException();
this.handler = handler;
}
Sets a new handler for unexecutable tasks. |
public void setThreadFactory(ThreadFactory threadFactory) {
if (threadFactory == null)
throw new NullPointerException();
this.threadFactory = threadFactory;
}
Sets the thread factory used to create new threads. |
public void shutdown() {
// Fail if caller doesn't have modifyThread permission
SecurityManager security = System.getSecurityManager();
if (security != null)
java.security.AccessController.checkPermission(shutdownPerm);
boolean fullyTerminated = false;
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
if (workers.size() > 0) {
// Check if caller can modify worker threads. This
// might not be true even if passed above check, if
// the SecurityManager treats some threads specially.
if (security != null) {
for (Worker w: workers)
security.checkAccess(w.thread);
}
int state = runState;
if (state == RUNNING) // don't override shutdownNow
runState = SHUTDOWN;
try {
for (Worker w: workers)
w.interruptIfIdle();
} catch(SecurityException se) {
// If SecurityManager allows above checks, but
// then unexpectedly throws exception when
// interrupting threads (which it ought not do),
// back out as cleanly as we can. Some threads may
// have been killed but we remain in non-shutdown
// state.
runState = state;
throw se;
}
}
else { // If no workers, trigger full termination now
fullyTerminated = true;
runState = TERMINATED;
termination.signalAll();
}
} finally {
mainLock.unlock();
}
if (fullyTerminated)
terminated();
}
Initiates an orderly shutdown in which previously submitted
tasks are executed, but no new tasks will be
accepted. Invocation has no additional effect if already shut
down. |
public List<Runnable> shutdownNow() {
// Almost the same code as shutdown()
SecurityManager security = System.getSecurityManager();
if (security != null)
java.security.AccessController.checkPermission(shutdownPerm);
boolean fullyTerminated = false;
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
if (workers.size() > 0) {
if (security != null) {
for (Worker w: workers)
security.checkAccess(w.thread);
}
int state = runState;
if (state != TERMINATED)
runState = STOP;
try {
for (Worker w : workers)
w.interruptNow();
} catch(SecurityException se) {
runState = state; // back out;
throw se;
}
}
else { // If no workers, trigger full termination now
fullyTerminated = true;
runState = TERMINATED;
termination.signalAll();
}
} finally {
mainLock.unlock();
}
if (fullyTerminated)
terminated();
return Arrays.asList(workQueue.toArray(EMPTY_RUNNABLE_ARRAY));
}
Attempts to stop all actively executing tasks, halts the
processing of waiting tasks, and returns a list of the tasks that were
awaiting execution.
This implementation cancels tasks via Thread#interrupt , so if any tasks mask or fail to respond to
interrupts, they may never terminate. |
protected void terminated() {
}
Method invoked when the Executor has terminated. Default
implementation does nothing. Note: To properly nest multiple
overridings, subclasses should generally invoke
super.terminated within this method. |
void workerDone(Worker w) {
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
completedTaskCount += w.completedTasks;
workers.remove(w);
if (--poolSize > 0)
return;
// Else, this is the last thread. Deal with potential shutdown.
int state = runState;
assert state != TERMINATED;
if (state != STOP) {
// If there are queued tasks but no threads, create
// replacement.
Runnable r = workQueue.poll();
if (r != null) {
addThread(r).start();
return;
}
// If there are some (presumably delayed) tasks but
// none pollable, create an idle replacement to wait.
if (!workQueue.isEmpty()) {
addThread(null).start();
return;
}
// Otherwise, we can exit without replacement
if (state == RUNNING)
return;
}
// Either state is STOP, or state is SHUTDOWN and there is
// no work to do. So we can terminate.
termination.signalAll();
runState = TERMINATED;
// fall through to call terminate() outside of lock.
} finally {
mainLock.unlock();
}
assert runState == TERMINATED;
terminated();
}
Perform bookkeeping for a terminated worker thread. |