BlockingQueue
|
|
BlockingQueue
可以作为多线程的数据共享通道,关键在于“Blocking”。
方法 | 描述 |
---|---|
boolean add(E e) | 添加成功,返回true;容量满抛出异常 |
boolean remove(Object o) | 删除成功,返回true;否则返回false |
boolean offer(E e) | 入队成功,返回true;否则返回false |
E poll(long timeout, TimeUnit unit) | 出队,返回元素;空队列返回null |
void put(E e) | 入队,队列满了会等待(Blocking) |
E take() | 出队,队列为空会等待(Blocking) |
常用的阻塞队列具体类有 ArrayBlockingQueue、LinkedBlockingQueue、PriorityBlockingQueue、LinkedBlockingDeque 等。
ArrayBlockingQueue
|
|
ArrayBlockingQueue
是一个基于数组且有界的阻塞队列。此队列按 FIFO(先进先出)原则对元素进行排序。
属性
内部元素用一个对象数组存储,等待通知机制是通过一个ReentrantLock
和两个Condition
实现的。
构造函数
|
|
等待
put
当队列满时,需要让压入线程等待在notFull
。
take
当队列为空时,当前线程等待在notEmpty
。
通知
dequeue
当有元素从队列中被挪走,队列中出现空位时,通知等待入队的线程notFull
。
enqueue
当队列中有新元素时,通知等待出队的线程notNull
。
LinkedBlockingQueue
|
|
LinkedBlockingQueue
是一个使用链表完成队列操作的阻塞队列。链表是单向链表,而不是双向链表。内部采用两把锁放锁和拿锁,所以读写可以同时进行。
属性
内部使用放锁和拿锁,这两个锁实现阻塞,所以元素数量存在竞态条件,这里使用原子类AtomicInteger
保证线程安全。
构造方法
|
|
等待和通知
LinkedBlockingQueue
和ArrayBlockingQueue
底层实现不同,由于有两个锁,在消费数据和插入数据时都有机会唤醒notFull
和notEmpty
。
ArrayBlockingQueue
是将通知放在enqueue()
和dequeue
中了。