001: /*
002: * Written by Doug Lea with assistance from members of JCP JSR-166
003: * Expert Group and released to the public domain, as explained at
004: * http://creativecommons.org/licenses/publicdomain
005: */
006:
007: package java.util.concurrent;
008:
009: import java.util.Collection;
010: import java.util.Queue;
011:
012: /**
013: * A {@link java.util.Queue} that additionally supports operations
014: * that wait for the queue to become non-empty when retrieving an element,
015: * and wait for space to become available in the queue when storing an
016: * element.
017: *
018: * <p>A <tt>BlockingQueue</tt> does not accept <tt>null</tt> elements.
019: * Implementations throw <tt>NullPointerException</tt> on attempts
020: * to <tt>add</tt>, <tt>put</tt> or <tt>offer</tt> a <tt>null</tt>. A
021: * <tt>null</tt> is used as a sentinel value to indicate failure of
022: * <tt>poll</tt> operations.
023: *
024: * <p>A <tt>BlockingQueue</tt> may be capacity bounded. At any given
025: * time it may have a <tt>remainingCapacity</tt> beyond which no
026: * additional elements can be <tt>put</tt> without blocking.
027: * A <tt>BlockingQueue</tt> without any intrinsic capacity constraints always
028: * reports a remaining capacity of <tt>Integer.MAX_VALUE</tt>.
029: *
030: * <p> While <tt>BlockingQueue</tt> is designed to be used primarily
031: * for producer-consumer queues, it additionally supports the {@link
032: * java.util.Collection} interface. So, for example, it is possible
033: * to remove an arbitrary element from a queue using
034: * <tt>remove(x)</tt>. However, such operations are in general
035: * <em>not</em> performed very efficiently, and are intended for only
036: * occasional use, such as when a queued message is cancelled. Also,
037: * the bulk Collection operations, most notably <tt>addAll</tt>, are
038: * <em>not</em> necessarily performed atomically, so it is possible
039: * for <tt>addAll(c)</tt> to fail (throwing an exception) after adding
040: * only some of the elements in <tt>c</tt>.
041: *
042: * <p>A <tt>BlockingQueue</tt> does <em>not</em> intrinsically support
043: * any kind of "close" or "shutdown" operation to
044: * indicate that no more items will be added. The needs and usage of
045: * such features tend to be implementation-dependent. For example, a
046: * common tactic is for producers to insert special
047: * <em>end-of-stream</em> or <em>poison</em> objects, that are
048: * interpreted accordingly when taken by consumers.
049: *
050: * <p>
051: * Usage example, based on a typical producer-consumer scenario.
052: * Note that a <tt>BlockingQueue</tt> can safely be used with multiple
053: * producers and multiple consumers.
054: * <pre>
055: * class Producer implements Runnable {
056: * private final BlockingQueue queue;
057: * Producer(BlockingQueue q) { queue = q; }
058: * public void run() {
059: * try {
060: * while(true) { queue.put(produce()); }
061: * } catch (InterruptedException ex) { ... handle ...}
062: * }
063: * Object produce() { ... }
064: * }
065: *
066: * class Consumer implements Runnable {
067: * private final BlockingQueue queue;
068: * Consumer(BlockingQueue q) { queue = q; }
069: * public void run() {
070: * try {
071: * while(true) { consume(queue.take()); }
072: * } catch (InterruptedException ex) { ... handle ...}
073: * }
074: * void consume(Object x) { ... }
075: * }
076: *
077: * class Setup {
078: * void main() {
079: * BlockingQueue q = new SomeQueueImplementation();
080: * Producer p = new Producer(q);
081: * Consumer c1 = new Consumer(q);
082: * Consumer c2 = new Consumer(q);
083: * new Thread(p).start();
084: * new Thread(c1).start();
085: * new Thread(c2).start();
086: * }
087: * }
088: * </pre>
089: *
090: * <p>This interface is a member of the
091: * <a href="{@docRoot}/../guide/collections/index.html">
092: * Java Collections Framework</a>.
093: *
094: * @since 1.5
095: * @author Doug Lea
096: * @param <E> the type of elements held in this collection
097: */
098: public interface BlockingQueue<E> extends Queue<E> {
099:
100: /**
101: * Inserts the specified element into this queue, if possible. When
102: * using queues that may impose insertion restrictions (for
103: * example capacity bounds), method <tt>offer</tt> is generally
104: * preferable to method {@link Collection#add}, which can fail to
105: * insert an element only by throwing an exception.
106: *
107: * @param o the element to add.
108: * @return <tt>true</tt> if it was possible to add the element to
109: * this queue, else <tt>false</tt>
110: * @throws NullPointerException if the specified element is <tt>null</tt>
111: */
112: boolean offer(E o);
113:
114: /**
115: * Inserts the specified element into this queue, waiting if necessary
116: * up to the specified wait time for space to become available.
117: * @param o the element to add
118: * @param timeout how long to wait before giving up, in units of
119: * <tt>unit</tt>
120: * @param unit a <tt>TimeUnit</tt> determining how to interpret the
121: * <tt>timeout</tt> parameter
122: * @return <tt>true</tt> if successful, or <tt>false</tt> if
123: * the specified waiting time elapses before space is available.
124: * @throws InterruptedException if interrupted while waiting.
125: * @throws NullPointerException if the specified element is <tt>null</tt>.
126: */
127: boolean offer(E o, long timeout, TimeUnit unit)
128: throws InterruptedException;
129:
130: /**
131: * Retrieves and removes the head of this queue, waiting
132: * if necessary up to the specified wait time if no elements are
133: * present on this queue.
134: * @param timeout how long to wait before giving up, in units of
135: * <tt>unit</tt>
136: * @param unit a <tt>TimeUnit</tt> determining how to interpret the
137: * <tt>timeout</tt> parameter
138: * @return the head of this queue, or <tt>null</tt> if the
139: * specified waiting time elapses before an element is present.
140: * @throws InterruptedException if interrupted while waiting.
141: */
142: E poll(long timeout, TimeUnit unit) throws InterruptedException;
143:
144: /**
145: * Retrieves and removes the head of this queue, waiting
146: * if no elements are present on this queue.
147: * @return the head of this queue
148: * @throws InterruptedException if interrupted while waiting.
149: */
150: E take() throws InterruptedException;
151:
152: /**
153: * Adds the specified element to this queue, waiting if necessary for
154: * space to become available.
155: * @param o the element to add
156: * @throws InterruptedException if interrupted while waiting.
157: * @throws NullPointerException if the specified element is <tt>null</tt>.
158: */
159: void put(E o) throws InterruptedException;
160:
161: /**
162: * Returns the number of elements that this queue can ideally (in
163: * the absence of memory or resource constraints) accept without
164: * blocking, or <tt>Integer.MAX_VALUE</tt> if there is no
165: * intrinsic limit.
166: * <p>Note that you <em>cannot</em> always tell if
167: * an attempt to <tt>add</tt> an element will succeed by
168: * inspecting <tt>remainingCapacity</tt> because it may be the
169: * case that a waiting consumer is ready to <tt>take</tt> an
170: * element out of an otherwise full queue.
171: * @return the remaining capacity
172: */
173: int remainingCapacity();
174:
175: /**
176: * Adds the specified element to this queue if it is possible to
177: * do so immediately, returning <tt>true</tt> upon success, else
178: * throwing an IllegalStateException.
179: * @param o the element
180: * @return <tt>true</tt> (as per the general contract of
181: * <tt>Collection.add</tt>).
182: *
183: * @throws NullPointerException if the specified element is <tt>null</tt>
184: * @throws IllegalStateException if element cannot be added
185: */
186: boolean add(E o);
187:
188: /**
189: * Removes all available elements from this queue and adds them
190: * into the given collection. This operation may be more
191: * efficient than repeatedly polling this queue. A failure
192: * encountered while attempting to <tt>add</tt> elements to
193: * collection <tt>c</tt> may result in elements being in neither,
194: * either or both collections when the associated exception is
195: * thrown. Attempts to drain a queue to itself result in
196: * <tt>IllegalArgumentException</tt>. Further, the behavior of
197: * this operation is undefined if the specified collection is
198: * modified while the operation is in progress.
199: *
200: * @param c the collection to transfer elements into
201: * @return the number of elements transferred.
202: * @throws NullPointerException if c is null
203: * @throws IllegalArgumentException if c is this queue
204: *
205: */
206: int drainTo(Collection<? super E> c);
207:
208: /**
209: * Removes at most the given number of available elements from
210: * this queue and adds them into the given collection. A failure
211: * encountered while attempting to <tt>add</tt> elements to
212: * collection <tt>c</tt> may result in elements being in neither,
213: * either or both collections when the associated exception is
214: * thrown. Attempts to drain a queue to itself result in
215: * <tt>IllegalArgumentException</tt>. Further, the behavior of
216: * this operation is undefined if the specified collection is
217: * modified while the operation is in progress.
218: *
219: * @param c the collection to transfer elements into
220: * @param maxElements the maximum number of elements to transfer
221: * @return the number of elements transferred.
222: * @throws NullPointerException if c is null
223: * @throws IllegalArgumentException if c is this queue
224: */
225: int drainTo(Collection<? super E> c, int maxElements);
226: }
|