Home | History | Annotate | Download | only in concurrent
      1 /*
      2  * Written by Doug Lea with assistance from members of JCP JSR-166
      3  * Expert Group and released to the public domain, as explained at
      4  * http://creativecommons.org/licenses/publicdomain
      5  */
      6 
      7 package java.util.concurrent;
      8 
      9 /**
     10  * An object that executes submitted {@link Runnable} tasks. This
     11  * interface provides a way of decoupling task submission from the
     12  * mechanics of how each task will be run, including details of thread
     13  * use, scheduling, etc.  An <tt>Executor</tt> is normally used
     14  * instead of explicitly creating threads. For example, rather than
     15  * invoking <tt>new Thread(new(RunnableTask())).start()</tt> for each
     16  * of a set of tasks, you might use:
     17  *
     18  * <pre>
     19  * Executor executor = <em>anExecutor</em>;
     20  * executor.execute(new RunnableTask1());
     21  * executor.execute(new RunnableTask2());
     22  * ...
     23  * </pre>
     24  *
     25  * However, the <tt>Executor</tt> interface does not strictly
     26  * require that execution be asynchronous. In the simplest case, an
     27  * executor can run the submitted task immediately in the caller's
     28  * thread:
     29  *
     30  * <pre>
     31  * class DirectExecutor implements Executor {
     32  *     public void execute(Runnable r) {
     33  *         r.run();
     34  *     }
     35  * }</pre>
     36  *
     37  * More typically, tasks are executed in some thread other
     38  * than the caller's thread.  The executor below spawns a new thread
     39  * for each task.
     40  *
     41  * <pre>
     42  * class ThreadPerTaskExecutor implements Executor {
     43  *     public void execute(Runnable r) {
     44  *         new Thread(r).start();
     45  *     }
     46  * }</pre>
     47  *
     48  * Many <tt>Executor</tt> implementations impose some sort of
     49  * limitation on how and when tasks are scheduled.  The executor below
     50  * serializes the submission of tasks to a second executor,
     51  * illustrating a composite executor.
     52  *
     53  *  <pre> {@code
     54  * class SerialExecutor implements Executor {
     55  *   final Queue<Runnable> tasks = new ArrayDeque<Runnable>();
     56  *   final Executor executor;
     57  *   Runnable active;
     58  *
     59  *   SerialExecutor(Executor executor) {
     60  *     this.executor = executor;
     61  *   }
     62  *
     63  *   public synchronized void execute(final Runnable r) {
     64  *     tasks.offer(new Runnable() {
     65  *       public void run() {
     66  *         try {
     67  *           r.run();
     68  *         } finally {
     69  *           scheduleNext();
     70  *         }
     71  *       }
     72  *     });
     73  *     if (active == null) {
     74  *       scheduleNext();
     75  *     }
     76  *   }
     77  *
     78  *   protected synchronized void scheduleNext() {
     79  *     if ((active = tasks.poll()) != null) {
     80  *       executor.execute(active);
     81  *     }
     82  *   }
     83  * }}</pre>
     84  *
     85  * The <tt>Executor</tt> implementations provided in this package
     86  * implement {@link ExecutorService}, which is a more extensive
     87  * interface.  The {@link ThreadPoolExecutor} class provides an
     88  * extensible thread pool implementation. The {@link Executors} class
     89  * provides convenient factory methods for these Executors.
     90  *
     91  * <p>Memory consistency effects: Actions in a thread prior to
     92  * submitting a {@code Runnable} object to an {@code Executor}
     93  * <a href="package-summary.html#MemoryVisibility"><i>happen-before</i></a>
     94  * its execution begins, perhaps in another thread.
     95  *
     96  * @since 1.5
     97  * @author Doug Lea
     98  */
     99 public interface Executor {
    100 
    101     /**
    102      * Executes the given command at some time in the future.  The command
    103      * may execute in a new thread, in a pooled thread, or in the calling
    104      * thread, at the discretion of the <tt>Executor</tt> implementation.
    105      *
    106      * @param command the runnable task
    107      * @throws RejectedExecutionException if this task cannot be
    108      * accepted for execution.
    109      * @throws NullPointerException if command is null
    110      */
    111     void execute(Runnable command);
    112 }
    113