ConcurrentLinkedDeque与LinkedBlockingDeque

我需要一个线程安全的LIFO结构,并发现我可以使用Deque线程安全实现。 Java 7引入了ConcurrentLinkedDeque ,Java 6引入了LinkedBlockingDeque

如果我只使用addFirst()的非阻塞方法,例如addFirst()removeFirst() ,它与ConcurrentLinkedDeque有什么区别吗?

即如果你忽略阻塞方面,除了LinkedBlockingDeque有界之外, ConcurrentLinkedDequeLinkedBlockingDeque之间是否还有其他区别?

两件事情:

1:如果我只使用addFirst()的非阻塞方法,例如addFirst()removeFirst() ,它与ConcurrentLinkedDeque有什么区别吗?

LinkedBlockingDeque ,这些方法在并发锁定行为方面确实存在差异:

 public E removeFirst() { E x = pollFirst(); .. } public E pollFirst() { lock.lock(); //Common lock for while list try { return unlinkFirst(); } finally { lock.unlock(); } } 

同样适用于addFirst方法。 在ConcurrentLinkedDeque这个方法的锁定行为是不同的,并且更有效,因为它不会锁定整个列表而是锁定它的一个子集,检查ConcurrentLinkedDeque源代码将使您更加清楚。

2:来自ConcurrentLinkedDeque javadoc:

请注意,与大多数集合不同,size方法不是恒定时间操作。

..

此外,批量操作addAll,removeAll,retainAll,containsAll,equals和toArray不保证以primefaces方式执行。

对于LinkedBlockingDeque上面的描述不正确

引用伟大的Doug Lea (我的重点)

LinkedBlockingDeque与ConcurrentLinkedDeque

LinkedBlockingDeque类旨在成为“标准”阻塞deque类。 当前实现具有相对低的开销但是相对较差的可伸缩性 。 …

ConcurrentLinkedDeque与LinkedBlockingDeque具有几乎相反的性能配置文件相对较高的开销,但非常好的可伸缩性 。 …在并发应用程序中,想要一个线程安全但不支持阻塞的Deque并不常见。 大多数那些做得更好的可能是特殊情况解决方案。

他似乎建议你应该使用LinkedBlockingDeque除非你特别需要ConcurrentLinkedDeque的function。

ConcuredntLinkedDequeue是无锁的(请参阅源代码中的注释),而LinkedBlockingQueue使用锁定。 那是前者应该更有效率

LinkedBlockingDeque和ConcurrentLinkedDeque都是线程安全的,但使用哪一个取决于您的应用程序要求。

例如,

LinkedBlockingDequeue:如果您希望一次只有单个线程可以对您的数据进行操作以及何时需要阻止您的应用程序,请使用此集合。

ConcurrentLinkedDeque:这也是线程安全的集合deque,如果你的应用程序是multithreading的,并且你希望你的每个线程都可以访问数据,那么ConcurrentLinkedDequeue是最好的选择。

在你的问题中,

1.我需要一个线程安全的LIFO结构,

如果您希望只有单个线程可以操作您的数据,请使用LinkedBlockingDeque。

如果您希望每个线程都可以访问共享数据,请使用ConcurrentLinkedDeque

2.如果忽略阻塞方面,ConcurrentLinkedDeque和LinkedBlockingDeque之间是否还有其他区别,

是的,因为LinkedBlockingDeque使用锁定机制并且ConcurrentLinkedDeque不是这样可能会影响您想要操作数据时的性能。