zoukankan      html  css  js  c++  java
  • ConcurrentLinkedQueue和LinkedBlockingQueue区别

    原创转载请注明出处:https://www.cnblogs.com/agilestyle/p/11394436.html

    线程安全队列类图


    两者的区别在于

    • ConcurrentLinkedQueue基于CAS的无锁技术,不需要在每个操作时使用锁,所以扩展性表现要更加优异,在常见的多线程访问场景,一般可以提供较高吞吐量。
    • LinkedBlockingQueue内部则是基于锁,并提供了BlockingQueue的等待性方法。

    BlockingQueue基本都是基于锁实现,比如典型的LinkedBlockingQueue


    有界队列

    • ArrayBlockingQueue是最典型的的有界队列,其内部以final的数组保存数据,数组的大小就决定了队列的边界,所以我们在创建ArrayBlockingQueue时,都要指定容量,如
    public ArrayBlockingQueue(int capacity, boolean fair) 
    • LinkedBlockingQueue,容易被误解为无边界,但其实其行为和内部代码都是基于有界的逻辑实现的,只不过如果我们没有在创建队列时就指定容量,那么其容量限制就自动被设置为Integer.MAX_VALUE,成为了无界队列。
    • SynchronousQueue,这是一个非常奇葩的队列实现,每个删除操作都要等待插入操作,反之每个插入操作也都要等待删除动作。那么这个队列的容量是多少呢?是1吗?其实不是的,其内部容量是0。

    无界队列

    • PriorityBlockingQueue是无边界的优先队列,虽然严格意义上来讲,其大小总归是要受系统资源影响。
    • DelayedQueue和LinkedTransferQueue同样是无边界的队列。对于无边界的队列,有一个自然的结果,就是put操作永远也不会发生其他BlockingQueue的那种等待情况。

    有界队列使用场景

    以LinkedBlockingQueue、ArrayBlockingQueue和SynchronousQueue为例,根据需求可以从很多方面考量:

    • 考虑应用场景中对队列边界的要求。ArrayBlockingQueue是有明确的容量限制的,而LinkedBlockingQueue则取决于我们是否在创建时指定,SynchronousQueue则干脆不能缓存任何元素。
    • 从空间利用角度,数组结构的ArrayBlockingQueue要比LinkedBlockingQueue紧凑,因为其不需要创建所谓节点,但是其初始分配阶段就需要一段连续的空间,所以初始内存需求更大。
    • 通用场景中,LinkedBlockingQueue的吞吐量一般优于ArrayBlockingQueue,因为它实现了更加细粒度的锁操作。
    • ArrayBlockingQueue实现比较简单,性能更好预测,属于表现稳定的“选手”。
    • 如果需要实现的是两个线程之间接力性(handoff)的场景,可能会选择CountDownLatch,但是SynchronousQueue也是完美符合这种场景的,而且线程间协调和数据传输统一起来,代码更加规范。
    • 可能令人意外的是,很多时候SynchronousQueue的性能表现,往往大大超过其他实现,尤其是在队列元素较小的场景。

    Reference

    https://time.geekbang.org/column/article/9588

    强者自救 圣者渡人
  • 相关阅读:
    开源项目:MMTweenAnimation
    URI跳转方式地图导航的代码实践
    处理i18n国际电话区号的代码实践
    图片变形的抗锯齿处理方法
    CocoaPods版本升级
    JSPatch 部署安全策略
    JSPatch实现原理详解<二>
    JSPatch实现原理详解
    JSPatch – 动态更新iOS APP
    iOS富文本组件的实现—DTCoreText源码解析 渲染篇
  • 原文地址:https://www.cnblogs.com/agilestyle/p/11394436.html
Copyright © 2011-2022 走看看