Class MultiThreadedQueue<E>

java.lang.Object
ca.spottedleaf.concurrentutil.collection.MultiThreadedQueue<E>
Type Parameters:
E - Type of element in this queue.
All Implemented Interfaces:
Iterable<E>, Collection<E>, Queue<E>
Direct Known Subclasses:
ReentrantAreaLock.Node

public class MultiThreadedQueue<E> extends Object implements Queue<E>
MT-Safe linked first in first out ordered queue. This queue should out-perform ConcurrentLinkedQueue in high-contention reads/writes, and is not any slower in lower contention reads/writes.

Note that this queue breaks the specification laid out by Collection, see preventAdds() and Collection.add(Object).

This queue will only unlink linked nodes through the peek() and poll() methods, and this is only if they are at the head of the queue.

  • Field Details

  • Constructor Details

    • MultiThreadedQueue

      public MultiThreadedQueue()
      Constructs a MultiThreadedQueue, initially empty.

      The returned object may not be published without synchronization.

    • MultiThreadedQueue

      public MultiThreadedQueue(Iterable<? extends E> collection)
      Constructs a MultiThreadedQueue, initially containing all elements in the specified collection.

      The returned object may not be published without synchronization.

      Parameters:
      collection - The specified collection.
      Throws:
      NullPointerException - If collection is null or contains null elements.
  • Method Details

    • setHeadPlain

      protected final void setHeadPlain(MultiThreadedQueue.LinkedNode<E> newHead)
    • setHeadOpaque

      protected final void setHeadOpaque(MultiThreadedQueue.LinkedNode<E> newHead)
    • getHeadPlain

      protected final MultiThreadedQueue.LinkedNode<E> getHeadPlain()
    • getHeadOpaque

      protected final MultiThreadedQueue.LinkedNode<E> getHeadOpaque()
    • getHeadAcquire

      protected final MultiThreadedQueue.LinkedNode<E> getHeadAcquire()
    • setTailPlain

      protected final void setTailPlain(MultiThreadedQueue.LinkedNode<E> newTail)
    • setTailOpaque

      protected final void setTailOpaque(MultiThreadedQueue.LinkedNode<E> newTail)
    • getTailPlain

      protected final MultiThreadedQueue.LinkedNode<E> getTailPlain()
    • getTailOpaque

      protected final MultiThreadedQueue.LinkedNode<E> getTailOpaque()
    • remove

      public E remove() throws NoSuchElementException
      Specified by:
      remove in interface Queue<E>
      Throws:
      NoSuchElementException
    • add

      public boolean add(E element)

      Contrary to the specification of Collection.add(E), this method will fail to add the element to this queue and return false if this queue is add-blocked.

      Specified by:
      add in interface Collection<E>
      Specified by:
      add in interface Queue<E>
    • forceAdd

      public boolean forceAdd(E element)
      Adds the specified element to the tail of this queue. If this queue is currently add-locked, then the queue is released from that lock and this element is added. The unlock operation and addition of the specified element is atomic.
      Parameters:
      element - The specified element.
      Returns:
      true if this queue previously allowed additions
    • element

      public E element() throws NoSuchElementException
      Specified by:
      element in interface Queue<E>
      Throws:
      NoSuchElementException
    • offer

      public boolean offer(E element)

      This method may also return false to indicate an element was not added if this queue is add-blocked.

      Specified by:
      offer in interface Queue<E>
    • peek

      public E peek()
      Specified by:
      peek in interface Queue<E>
    • poll

      public E poll()
      Specified by:
      poll in interface Queue<E>
    • pollIf

      public E pollIf(Predicate<E> predicate)
      Retrieves and removes the head of this queue if it matches the specified predicate. If this queue is empty or the head does not match the predicate, this function returns null.

      The predicate may be invoked multiple or no times in this call.

      Parameters:
      predicate - The specified predicate.
      Returns:
      The head if it matches the predicate, or null if it did not or this queue is empty.
    • clear

      public void clear()
      Specified by:
      clear in interface Collection<E>
    • preventAdds

      public boolean preventAdds()
      Prevents elements from being added to this queue. Once this is called, any attempt to add to this queue will fail.

      This function is MT-Safe.

      Returns:
      true if the queue was modified to prevent additions, false if it already prevented additions.
    • allowAdds

      public void allowAdds()
      Allows elements to be added to this queue once again. Note that this function has undefined behaviour if preventAdds() is not called beforehand. The benefit of this function over tryAllowAdds() is that this function might perform better.

      This function is not MT-Safe.

    • tryAllowAdds

      public boolean tryAllowAdds()
      Tries to allow elements to be added to this queue. Returns true if the queue was previous add-locked, false otherwise.

      This function is MT-Safe, however it should not be used with allowAdds().

      Returns:
      true if the queue was previously add-locked, false otherwise.
    • addOrAllowAdds

      public boolean addOrAllowAdds(E element)
      Atomically adds the specified element to this queue or allows additions to the queue. If additions are not allowed, the element is not added.

      This function is MT-Safe.

      Parameters:
      element - The specified element.
      Returns:
      true if the queue now allows additions, false if the element was added.
    • isAddBlocked

      public boolean isAddBlocked()
      Returns whether this queue is currently add-blocked. That is, whether add(Object) and friends will return false.
    • pollOrBlockAdds

      public E pollOrBlockAdds()
      Atomically removes the head from this queue if it exists, otherwise prevents additions to this queue if no head is removed.

      This function is MT-Safe.

      If the queue is already add-blocked and empty then no operation is performed.
      Returns:
      null if the queue is now add-blocked or was previously add-blocked, else returns an non-null value which was the previous head of queue.
    • remove

      public boolean remove(Object object)
      Specified by:
      remove in interface Collection<E>
    • removeIf

      public boolean removeIf(Predicate<? super E> filter)
      Specified by:
      removeIf in interface Collection<E>
    • removeAll

      public boolean removeAll(Collection<?> collection)
      Specified by:
      removeAll in interface Collection<E>
    • retainAll

      public boolean retainAll(Collection<?> collection)
      Specified by:
      retainAll in interface Collection<E>
    • toArray

      public Object[] toArray()
      Specified by:
      toArray in interface Collection<E>
    • toArray

      public <T> T[] toArray(T[] array)
      Specified by:
      toArray in interface Collection<E>
    • toArray

      public <T> T[] toArray(IntFunction<T[]> generator)
      Specified by:
      toArray in interface Collection<E>
    • toString

      public String toString()
      Overrides:
      toString in class Object
    • addAll

      public boolean addAll(Collection<? extends E> collection)
      Adds all elements from the specified collection to this queue. The addition is atomic.
      Specified by:
      addAll in interface Collection<E>
      Parameters:
      collection - The specified collection.
      Returns:
      true if all elements were added successfully, or false if this queue is add-blocked, or false if the specified collection contains no elements.
    • addAll

      public boolean addAll(Iterable<? extends E> iterable)
      Adds all elements from the specified iterable object to this queue. The addition is atomic.
      Parameters:
      iterable - The specified iterable object.
      Returns:
      true if all elements were added successfully, or false if this queue is add-blocked, or false if the specified iterable contains no elements.
    • addAll

      public boolean addAll(E[] items)
      Adds all of the elements from the specified array to this queue.
      Parameters:
      items - The specified array.
      Returns:
      true if all elements were added successfully, or false if this queue is add-blocked, or false if the specified array has a length of 0.
    • addAll

      public boolean addAll(E[] items, int off, int len)
      Adds all of the elements from the specified array to this queue.
      Parameters:
      items - The specified array.
      off - The offset in the array.
      len - The number of items.
      Returns:
      true if all elements were added successfully, or false if this queue is add-blocked, or false if the specified array has a length of 0.
    • containsAll

      public boolean containsAll(Collection<?> collection)
      Specified by:
      containsAll in interface Collection<E>
    • iterator

      public Iterator<E> iterator()
      Specified by:
      iterator in interface Collection<E>
      Specified by:
      iterator in interface Iterable<E>
    • size

      public int size()

      Note that this function is computed non-atomically and in O(n) time. The value returned may not be representative of the queue in its current state.

      Specified by:
      size in interface Collection<E>
    • isEmpty

      public boolean isEmpty()
      Specified by:
      isEmpty in interface Collection<E>
    • contains

      public boolean contains(Object object)
      Specified by:
      contains in interface Collection<E>
    • find

      public E find(Predicate<E> predicate)
      Finds the first element in this queue that matches the predicate.
      Parameters:
      predicate - The predicate to test elements against.
      Returns:
      The first element that matched the predicate, null if none matched.
    • forEach

      public void forEach(Consumer<? super E> action)
      Specified by:
      forEach in interface Iterable<E>
    • forceAppendList

      protected final boolean forceAppendList(MultiThreadedQueue.LinkedNode<E> head, MultiThreadedQueue.LinkedNode<E> tail)
    • appendList

      protected final boolean appendList(MultiThreadedQueue.LinkedNode<E> head, MultiThreadedQueue.LinkedNode<E> tail)
    • removeHead

      protected final E removeHead(Predicate<E> predicate)
    • removeHead

      protected final E removeHead()
    • drain

      public int drain(Consumer<E> consumer)
      Empties the queue into the specified consumer. This function is optimized for single-threaded reads, and should be faster than a loop on poll().

      This function is not MT-Safe. This function cannot be called with other read operations (peek(), poll(), clear(), etc). Write operations are safe to be called concurrently.

      Parameters:
      consumer - The consumer to accept the elements.
      Returns:
      The total number of elements drained.
    • drain

      public int drain(Consumer<E> consumer, boolean preventAdds)
      Empties the queue into the specified consumer. This function is optimized for single-threaded reads, and should be faster than a loop on poll().

      If preventAdds is true, then after this function returns the queue is guaranteed to be empty and additions to the queue will fail.

      This function is not MT-Safe. This function cannot be called with other read operations (peek(), poll(), clear(), etc). Write operations are safe to be called concurrently.

      Parameters:
      consumer - The consumer to accept the elements.
      preventAdds - Whether to prevent additions to this queue after draining.
      Returns:
      The total number of elements drained.
    • drain

      public int drain(Consumer<E> consumer, boolean preventAdds, Consumer<Throwable> exceptionHandler)
      Empties the queue into the specified consumer. This function is optimized for single-threaded reads, and should be faster than a loop on poll().

      If preventAdds is true, then after this function returns the queue is guaranteed to be empty and additions to the queue will fail.

      This function is not MT-Safe. This function cannot be called with other read operations (peek(), poll(), clear(), remove(Object) etc). Only write operations are safe to be called concurrently.

      Parameters:
      consumer - The consumer to accept the elements.
      preventAdds - Whether to prevent additions to this queue after draining.
      exceptionHandler - Invoked when the consumer raises an exception.
      Returns:
      The total number of elements drained.
    • spliterator

      public Spliterator<E> spliterator()
      Specified by:
      spliterator in interface Collection<E>
      Specified by:
      spliterator in interface Iterable<E>