18

我认为,在大多数情况下,ArrayBlockingQueue将比LinkedBlockingQueue. 但是,当数组中总是有足够的空间时就是这种情况……如果它已满,那么它是否会表现得这么好就不是很可预测了,因为它会阻塞试图将数据推送到队列中的线程。 .

所以,我的问题是:是否有任何中间立场实施BlockingQueue?说,一个ArrayListBlockingQueue或一个BucketListBlockingQueue?类似于数组列表的东西,以便队列可以动态增加容量,同时仍然可以从使用数组最终存储数据中获得合理的好处?

4

2 回答 2

14

1. LinkedBlockingQueueLinkedList实现但不完全是JDK的实现LinkedList。它用于static inner class Node维护元素之间的链接)

Constructor for LinkedBlockingQueue
public LinkedBlockingQueue(int capacity) 
{
        if (capacity < = 0) throw new IllegalArgumentException();
        this.capacity = capacity;
        last = head = new Node< E >(null);   // Maintains a underlying linkedlist. ( Use when size is not known )
}

Node用于维护链接的类

static class Node<E> {
    E item;
    Node<E> next;
    Node(E x) { item = x; }
}

2. ArrayBlockingQueue(数组实现)

构造函数ArrayBlockingQueue

public ArrayBlockingQueue(int capacity, boolean fair) 
{
            if (capacity < = 0)
                throw new IllegalArgumentException();
            this.items = new Object[capacity]; // Maintains a underlying array
            lock = new ReentrantLock(fair);
            notEmpty = lock.newCondition();
            notFull =  lock.newCondition();
}

ArrayBlockingQueue和之间的最大区别LinkedBlockingQueue从构造函数中可以清楚地看出,一个具有 的底层数据结构,Array另一个具有LinkedList.

ArrayBlockingQueue使用单锁双条件算法LinkedBlockingQueue是“双锁队列”算法的变体,它有 2 个锁 2 个条件(takeLock,putLock)

到目前为止,我对这两种实现进行了比较回到原来的问题, 在这个 doug Lea 谈论 DynamicArrayBlockingQueue的并发邮件列表中提出了类似的问题,这是由 Dawid Kurzyniec 提供的实现。

于 2013-12-12T13:07:02.453 回答
8

我的 2 美分:

首先,这里的底线是您并不真正关心这里的差异,因为即使您使用普通的 LinkedBlockingQueue,当您交付一些微秒级系统时,性能也足够好。所以这里的性能差异并不是那么大。

如果您正在编写任务关键型高性能系统,并且您正在使用队列在线程之间传递消息,则您始终可以通过 [队列大小] = [最大可接受延迟] * [最大消息速率]来估计所需的队列大小。任何可以超过这种容量的东西都意味着你会遇到消费缓慢的问题。在关键任务应用程序中,这种延迟意味着您的系统出现故障。可能需要一些手动过程来确保系统正常运行。

如果您的系统不是关键任务,您可以简单地暂停(阻止)发布者,直到一些消费者可用。

于 2013-07-04T04:36:53.067 回答