六个方法
- add 增加一个元索 如果队列已满,则抛出一个IIIegaISlabEepeplian异常
- remove 移除并返回队列头部的元素 如果队列为空,则抛出一个NoSuchElementException异常
- element 返回队列头部的元素 如果队列为空,则抛出一个NoSuchElementException异常
- offer 添加一个元素并返回true 如果队列已满,则返回false
- poll 移除并返问队列头部的元素 如果队列为空,则返回null
- peek 返回队列头部的元素 如果队列为空,则返回null
阻塞队列中有的方法
- put 添加一个元素 如果队列满,则阻塞
- take 移除并返回队列头部的元素 如果队列为空,则阻塞
一些阻塞队列
ArrayBlockingQueue
ArrayBlockingQueue是基于数组(array-based)的先进先出(FIFO)有界(bounded)阻塞队列。
- 创建队列时,必须要指定队列容量(capacity),即数组大小。
- 创建队列时,可以传入Collection来初始化队列元素。
- 队列一旦被创建,那么队列容量不能被改变。
- 队列支持公平模式和非公平模式,默认非公平模式。
- 队列中只有一把锁,写锁和读锁未分离,并发控制采用了经典的two-condition(notEmpty、notFull)算法。
- 在生产和消费的时候,需要创建Node节点对象进行插入或移除,大批量数据的系统中,其对于GC的压力会比较大。
LinkedBlockingQueue
LinkedBlockingQueue是基于链表(linked nodes)的先进先出(FIFO)的可选界(optionally-bounded)的阻塞队列。
- 创建队列时,可以指定队列容量(capacity);如果不指定队列容量,那么默认队列容量为Integer.MAX_VALUE。
- 创建队列时,可以可以传入Collection来初始化队列元素,此时不能指定队列容量,默认为Integer.MAX_VALUE。
- 队列中的count即当前队列元素个数,采用AtomicInteger,避免put和take的竞争。
- 与ArrayBlockingQueue不同的是,LinkedBlockingQueue队列中有两把锁,读锁和写锁是分离的。
LinkedBlockingQueue内部维护的是一个链表结构。 - 而ArrayBlockingQueue内部维护了一个数组在生产和消费的时候,是直接将枚举对象插入或移除的,不会产生或销毁任何额外的对象实例。
- 使用了一个AtomicInteger对象来统计元素的个数。
PriorityBlockingQueue
PriorityBlockingQueue是基于数组(array based)的支持优先级的无界(unbounded)的阻塞队列。此队列的数据结构是堆
- 创建队列时,如果指定初始化容量(initialCapacity),那么默认初始化容量DEFAULT_INITIAL_CAPACITY为11。
- 创建队列时,可以指定队列初始化容量(initialCapacity),不是队列容量(capacity)。
- PriorityBlockingQueue的无界是指不能在创建队列时,指定队列的最大容量(capacity),并不是说PriorityBlockingQueue本身无界。最大容量是MAX_ARRAY_SIZE=Integer.MAX_VALUE-8。
- PriorityBlockingQueue无界的另一个意思就是生产者线程不会因为队列满了就阻塞,因为队列是无界的,没有容量满了这一说。offer(E e, long timeout, TimeUnit unit)的后两个参数没有任何作用查看源代码发现,其方法的实现直接是调用了offer(e)。但是当队列为空时,take仍然会阻塞。
- PriorityBlockingQueue通过数组来实现队列,在原有数组满了的情况下,通过复制数组来扩展队列容量,如果新扩展的数组容量大小超过MAX_ARRAY_SIZE,那么抛出OutOfMemoryError异常。
- 默认情况下元素采取自然顺序排列,也可以通过比较器comparator来指定元素的排序规则。元素按照升序排列。