Java集合(20)——并发集合(8)——阻塞队列(1)——ArrayBlockingQueue源码分析

目录

1.概述

2.使用案例

3.源码分析

3.1 重要属性

3.2 构造方法

3.3 私有方法入队与出队

(1)入队

(2)出队

3.4 put和take方法

(1)put

(2)take

3.5 offer和poll

(1)offer

(2)poll

3.6 peek

3.7 remainingCapacity

3.8  remove

4.总结


1.概述

  • ArrayBlockingQueue 是 BlockingQueue 接口的有界阻塞队列实现类,底层采用数组来实现。

特点

  • ArrayBlockingQueue一旦创建,容量不能改变。
  • 其并发控制采用可重入锁来控制,不管是插入操作还是读取操作,都需要获取到锁才能进行操作。
  • ArrayBlockingQueue 默认情况下不能保证线程访问队列的公平性,
    • 所谓公平性是指严格按照线程等待的绝对时间顺序,即最先等待的线程能够最先访问到 ArrayBlockingQueue。
    • 而非公平性则是指访问 ArrayBlockingQueue 的顺序不是遵守严格的时间顺序,有可能存在,

当 ArrayBlockingQueue 可以被访问时,长时间阻塞的线程依然无法访问到 ArrayBlockingQueue。如果保证公平性,通常会降低吞吐量。如果需要获得公平性的 ArrayBlockingQueue,可采用如下代码:

private static ArrayBlockingQueue<Integer> blockingQueue = new ArrayBlockingQueue<Integer>(10,true);

2.使用案例

使用案例见上一篇博客:https://blog.csdn.net/qq_34805255/article/details/101924873

 

3.源码分析

3.1 重要属性

public class ArrayBlockingQueue {

    /**
     * ArrayBlockingQueue的底层实现为此数组
     *
     * 并且可以看到此数组被final修饰,数组一旦创建,容量不可变(数组本身的性质),并且,数组引用指向的数组对象不可变
     */
    final Object[] items;

    /**
     * 队首索引位置
     */
    int takeIndex;

    /**
     * 队尾索引位置
     */
    int putIndex;

    /**
     * 队列中元素的个数
     */
    int count;


    /**
     * 采用ReentrantLock来保证线程安全
     */
    final ReentrantLock lock;

    /**
     * 为了保证消费(take)数据的时候如果为空的时候,进行阻塞(等待),使用了Condition
     *
     * 当获取数据的消费者线程被阻塞时会将该线程放置到notEmpty等待队列中(notEmpty可以理解为等待队列不空的等待队列)
     */
    private final Condition notEmpty;

    /**
     * 为了保证生产(put)数据的时候如果队列满的时候,进行阻塞(等待),使用了Condition
     *
     * 当插入数据的生产者线程被阻塞时,会将该线程放置到notFull等待队列中(notFull可以理解为等待队列不满的等待队列)。
     */
    private final Condition notFull;

}
  • 底层采用final数组items实现
  • 使用锁ReentrantLock保证线程安全
  • 使用两个Condition来实现阻塞

3.2 构造方法

    /**
     * 我们在创建一个ArrayBlockingQueue时,必须传入容量用做创建数组的大小
     * 
     * 当我们不传入是否使用公平锁时,默认是非公平的
     */
    public ArrayBlo
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值