SynchronousQueue同步队列原理及在线程池中的使用!

918 阅读2分钟

什么是SynchronousQueue同步队列?

synchronousQueue是一个特殊的、没有容量的阻塞队列。

同步队列的使用

Excutors中用于线程池

// Excutors中的静态方法,申明线程池用于处理任务。
// 该线程池核心线程数为0,最大线程数量为最大整数(基本由硬件资源决定负载上限了),线程空闲超时时间为60秒,任务队列为同步队列,容量为0。
// 表示有任务进来,则利用空闲线程或新增线程进行处理。适用于短任务场景,提高处理效率。
public static ExecutorService newCachedThreadPool() {
    return new ThreadPoolExecutor(0, Integer.MAX_VALUE,
                                  60L, TimeUnit.SECONDS,
                                  new SynchronousQueue<Runnable>());
}
// 公平同步队列对象,默认是非公平锁。可以在声明中指定。
new SynchronousQueue<T>(true);
// 非公平同步队列
new SynchronousQueue<T>();

TCPTransport中用于连接池

private static final ExecutorService connectionThreadPool =
    new ThreadPoolExecutor(0, maxConnectionThreads,
        threadKeepAliveTime, TimeUnit.MILLISECONDS,
        new SynchronousQueue<Runnable>(),
        new ThreadFactory() {
            public Thread newThread(Runnable runnable) {
                return AccessController.doPrivileged(new NewThreadAction(
                    runnable, "TCP Connection(idle)", true, true));
            }
        });

同步队列的实现

同步队列继承了抽象队列,并实现了阻塞队列

// 同步队列继承了抽象队列,并实现了阻塞队列
public class SynchronousQueue<E> extends AbstractQueue<E>
    implements BlockingQueue<E>, java.io.Serializable {}

由于同步队列容量为空,所以对一些通用队列方法做了简单的实现

// 实现方法也很简单,由于容量为空,所以对一些方法直接返回默认值,如isEmpty,size,contains,remove,peek等等
public boolean isEmpty() {return true;}
public int size() {return 0;}
public int remainingCapacity() {return 0;}
// 不做任何事情,因为同步队列没有容量
public void clear() {}
public boolean contains(Object o) {return false;}
public boolean remove(Object o) {return false;}
public boolean containsAll(Collection<?> c) {return c.isEmpty();}
public boolean removeAll(Collection<?> c) {return false;}
public boolean retainAll(Collection<?> c) {return false;}
public E peek() {return null;}
// 返回空的迭代器对象
public Iterator<E> iterator() {return Collections.emptyIterator();}
public Spliterator<E> spliterator() {return Spliterators.emptySpliterator();}
// 返回空的数组对象
public Object[] toArray() {return new Object[0];}

同步队列使用内部类TransferQueue实现同步阻塞与匹配功能。同步队列是公平还是非公平机制也是在这里实现。

主要通过CAS来完成任务同步。

// 使用内部类TransferQueue队列来实现同步阻塞与匹配功能。
abstract static class Transferer<E> {
        // 用于队列的出队入队都用到该方法。
        abstract E transfer(E e, boolean timed, long nanos);
}
// 双端栈
static final class TransferStack<E> extends Transferer<E> {}
// 双端队列
static final class TransferQueue<E> extends Transferer<E> {}

具体实现原理可参考:

juejin.cn/post/696181… juejin.cn/post/708945…