關於concurrent包下的阻塞佇列
在前面幾篇文章中,我們討論了同步容器(Hashtable、Vector),也討論了併發容器(ConcurrentHashMap、CopyOnWriteArrayList),這些工具都為我們編寫多執行緒程式提供了很大的方便。今天我們來討論另外一類容器:阻塞佇列。
在前面我們接觸的佇列都是非阻塞佇列,比如PriorityQueue、LinkedList(LinkedList是雙向連結串列,它實現了Dequeue介面)。
使用非阻塞佇列的時候有一個很大問題就是:它不會對當前執行緒產生阻塞,那麼在面對類似消費者-生產者的模型時,就必須額外地實現同步策略以及執行緒間喚醒策略,這個實現起來就非常麻煩。但是有了阻塞佇列就不一樣了,它會對當前執行緒產生阻塞,比如一個執行緒從一個空的阻塞佇列中取元素,此時執行緒會被阻塞直到阻塞佇列中有了元素。當佇列中有元素後,被阻塞的執行緒會自動被喚醒(不需要我們編寫程式碼去喚醒)。這樣提供了極大的方便性。
本文先講述一下java.util.concurrent包下提供主要的幾種阻塞佇列,然後分析了阻塞佇列和非阻塞佇列的中的各個方法,接著分析了阻塞佇列的實現原理,最後給出了一個實際例子和幾個使用場景。
一.幾種主要的阻塞佇列
二.阻塞佇列中的方法 VS 非阻塞佇列中的方法
三.阻塞佇列的實現原理
四.示例和使用場景
若有不正之處請多多諒解,並歡迎批評指正。
請尊重作者勞動成果,轉載請標明原文連結:
http://www.cnblogs.com/dolphin0520/p/3932906.html
一.幾種主要的阻塞佇列
自從Java 1.5之後,在java.util.concurrent包下提供了若干個阻塞佇列,主要有以下幾個:
ArrayBlockingQueue:基於陣列實現的一個阻塞佇列,在建立ArrayBlockingQueue物件時必須制定容量大小。並且可以指定公平性與非公平性,預設情況下為非公平的,即不保證等待時間最長的佇列最優先能夠訪問佇列。
LinkedBlockingQueue:基於連結串列實現的一個阻塞佇列,在建立LinkedBlockingQueue物件時如果不指定容量大小,則預設大小為Integer.MAX_VALUE。
PriorityBlockingQueue:以上2種佇列都是先進先出佇列,而PriorityBlockingQueue卻不是,它會按照元素的優先順序對元素進行排序,按照優先順序順序出隊,每次出隊的元素都是優先順序最高的元素。注意,此阻塞佇列為無界阻塞佇列,即容量沒有上限(通過原始碼就可以知道,它沒有容器滿的訊號標誌),前面2種都是有界佇列。
DelayQueue:基於PriorityQueue,一種延時阻塞佇列,DelayQueue中的元素只有當其指定的延遲時間到了,才能夠從佇列中獲取到該元素。DelayQueue也是一個無界佇列,因此往佇列中插入資料的操作(生產者)永遠不會被阻塞,而只有獲取資料的操作(消費者)才會被阻塞。
二.阻塞佇列中的方法 VS 非阻塞佇列中的方法
1.非阻塞佇列中的幾個主要方法:
add(E e):將元素e插入到佇列末尾,如果插入成功,則返回true;如果插入失敗(即佇列已滿),則會丟擲異常;
remove():移除隊首元素,若移除成功,則返回true;如果移除失敗(佇列為空),則會丟擲異常;
offer(E e):將元素e插入到佇列末尾,如果插入成功,則返回true;如果插入失敗(即佇列已滿),則返回false;
poll():移除並獲取隊首元素,若成功,則返回隊首元素;否則返回null;
peek():獲取隊首元素,若成功,則返回隊首元素;否則返回null
對於非阻塞佇列,一般情況下建議使用offer、poll和peek三個方法,不建議使用add和remove方法。因為使用offer、poll和peek三個方法可以通過返回值判斷操作成功與否,而使用add和remove方法卻不能達到這樣的效果。注意,非阻塞佇列中的方法都沒有進行同步措施。
2.阻塞佇列中的幾個主要方法:
阻塞佇列包括了非阻塞佇列中的大部分方法,上面列舉的5個方法在阻塞佇列中都存在,但是要注意這5個方法在阻塞佇列中都進行了同步措施。除此之外,阻塞佇列提供了另外4個非常有用的方法:
put(E e)
take()
offer(E e,long timeout, TimeUnit unit)
poll(long timeout, TimeUnit unit)
put方法用來向隊尾存入元素,如果佇列滿,則等待;
take方法用來從隊首取元素,如果佇列為空,則等待;
offer方法用來向隊尾存入元素,如果佇列滿,則等待一定的時間,當時間期限達到時,如果還沒有插入成功,則返回false;否則返回true;
poll方法用來從隊首取元素,如果佇列空,則等待一定的時間,當時間期限達到時,如果取到,則返回null;否則返回取得的元素;
三.阻塞佇列的實現原理
前面談到了非阻塞佇列和阻塞佇列中常用的方法,下面來探討阻塞佇列的實現原理,本文以ArrayBlockingQueue為例,其他阻塞佇列實現原理可能和ArrayBlockingQueue有一些差別,但是大體思路應該類似,有興趣的朋友可自行檢視其他阻塞佇列的實現原始碼。
首先看一下ArrayBlockingQueue類中的幾個成員變數:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
public class ArrayBlockingQueue<E> extends AbstractQueue<E>
implements BlockingQueue<E>,
java.io.Serializable {
private static final long serialVersionUID
= -817911632652898426L;
/**
The queued items */
private final E[]
items;
/**
items index for next take, poll or remove */
private int takeIndex;
/**
items index for next put, offer, or add. */
private int putIndex;
/**
Number of items in the queue */
private int count;
/*
*
Concurrency control uses the classic two-condition algorithm
*
found in any textbook.
*/
/**
Main lock guarding all access */
private final ReentrantLock
lock;
/**
Condition for waiting takes */
private final Condition
notEmpty;
相關推薦關於concurrent包下的阻塞佇列在前面幾篇文章中,我們討論了同步容器(Hashtable、Vector),也討論了併發容器(ConcurrentHashMap、CopyOnWriteArrayList),這些工具都為我們編寫多執行緒程式提供了很大的方便。今天我們來討論另外一類容器:阻塞佇列。 Java基礎知識-java.util.concurrent包下常見類的使用finall iss con value 通信 out 否則 app ted 一,Condition 一個場景,兩個線程數數,同時啟動兩個線程,線程A數1、2、3,然後線程B數4、5、6,最後線程A數7、8、9,程序結束,這涉及到線程之間的通信。 public class 併發包非阻塞佇列ConcurrentLinkedQueuejdk1.7.0_79 佇列是一種非常常用的資料結構,一進一出,先進先出。 在Java併發包中提供了兩種型別的佇列,非阻塞佇列與阻塞佇列,當然它們都是執行緒安全的,無需擔心在多執行緒併發環境所帶來的不可預知的問題。為什麼會有非阻塞和阻塞之分呢?這裡的非 java.util.concurrent包下同步輔助工具類CountDownLatchCountDownLatch作為一個輔助工具類,它允許一個或多個執行緒等待一系列指定操作的完成。CountDownLatch以一個給定值進行初始化,通過CountDownLatch cd java.util.concurrent包下的類 (轉)文章整理來源:http://www.cnblogs.com/aurawing/articles/1887056.html 一 ,背景: 在JDK1.5之前,Java中要進行業務併發時,通常需要有程式設計師獨立完成程式碼實現,當然也有一些開源的框架提供了這些功能,但是這些依然沒有JDK自帶的功 JAVA中常用的高階集合類總結(包含Concurrent包下的併發集合類)MAP WeakHashMap 和普通的HashMap相比,當除了自身有對key的引用外,此key沒有其他引用那麼此map會自動丟棄此值,從而解決HashMap物件中key-value資源無法釋放,導 執行緒併發執行緒安全介紹及java.util.concurrent包下類介紹執行緒Thread,在Java開發中多執行緒是必不可少的,但是真正能用好的並不多! 首先開啟一個執行緒三種方式 ①new Thread(Runnable).start() ②thread.star java.util.concurrent包下的幾個常用類1.Callable<V> Callable<V>與Runnable類似,理解Callable<V>可以從比較其與Runnable的區別開始: 1)從使用上:實現的Callable<V>的類需要實現call()方法,此方 【一】關於java.util.concurrent包下的併發類(atomic)併發類包除了java.util.concurrent之外,還有java.util.concurrent.atomic和java.util.concurrent.lock.java.util.concurrent中主要是一些關於集合框架的併發實現,例如ConcurrentHas 掌握併發包下的佇列說到佇列尤其是阻塞佇列,不得不說jdk的併發包(Java.util.concurrent)中的相關資料結構,今天我們就來對java(JDK1.7)中的佇列做一個總結。 1、Queue 佇列介面,定義了佇列基本的介面方法 前兩個方法是往佇列塞資料,在佇列空間不足的情況 ConCurrent包下工具類-CountDownLatchCountDownLatch是JAVA提供在java.util.concurrent包下的一個輔助類,可以把它看成是一個計數器,其內部維護著一個count計數,只不過對這個計數器的操作都是原子操作,同時只能有一個執行緒去操作這個計數器,CountDownLatc Java併發包下的阻塞佇列本文簡要介紹一下什麼是阻塞佇列,Java併發包給我們提供的阻塞佇列有哪些,以及怎麼去簡單使用 阻塞佇列 BlockingQueue 1. 簡單概念 阻塞佇列(BlockingQueue)是一個支援兩個附加操作的佇列:支援阻塞的插入和移除: 支援阻塞 死磕java concurrent包系列(三)基於ReentrantLock理解AQS的條件佇列基於Codition分析AQS的條件佇列 前言 上一篇我們講了AQS中的同步佇列佇列,現在我們研究一下條件佇列。 在java中最常見的加鎖方式就是synchorinzed和Reentrantlock,我們都說Reentrantlock比synchorinzed更加靈活,其實就靈活在Reentrantlock中 jdk提供的阻塞佇列BlockingQueue下的五個實現簡單操作以及介紹package cn.yarne.com.base.test; import java.util.Collections; import java.util.Date; import java.util.Iterator; import java.util.Vector; 死磕java concurrent包系列(五)基於AQS的條件佇列把LinkedBlockingQueue“扒光”LinkedBlockingQueue的基礎 LinkedBlockingQueue是一個基於連結串列的阻塞佇列,實際使用上與ArrayBlockingQueue完全一樣,我們只需要把之前烤雞的例子中的Queue物件替換一下即可。如果對於ArrayBlockingQueue不熟悉,可以去看看https:// 併發程式設計-concurrent指南-阻塞佇列BlockingQueue阻塞佇列BlockingQueue,java.util.concurrent下的BlockingQueue介面表示一個執行緒放入和提取例項的佇列。 適用場景: BlockingQueue通常用於一個執行緒生產物件,而另一個執行緒消費物件的場景。 一個執行緒往裡面放,另一個執行緒從裡面取的一個Bloc 併發程式設計-concurrent指南-阻塞佇列-優先順序的阻塞佇列PriorityBlockingQueuePriorityBlockingQueue是一個支援優先順序的無界阻塞佇列。 它使用了和類 java.util.PriorityQueue 一樣的排序規則。你無法向這個佇列中插入 null 值。 所有插入到 PriorityBlockingQueue 的元素必須實現 java.lang.Comparabl Java 使用阻塞佇列 BlockingQueue 多執行緒搜尋目錄及子目錄下包含關鍵字所有檔案Java 使用阻塞佇列 BlockingQueue 多執行緒在一個目錄及它的所以子目錄下搜尋所有檔案,打印出包含關鍵字的行 阻塞佇列( blocking queue ) 生產者執行緒向佇列插人元素, 消費者執行緒則取出它們。使用佇列,可以安全地從一個執行緒向另一個執行緒傳遞資料。 java concurrent包自帶執行緒池和佇列詳細講解Java執行緒池使用說明一簡介執行緒的使用在java中佔有極其重要的地位,在jdk1.4極其之前的jdk版本中,關於執行緒池的使用是極其簡陋的。在jdk1.5之後這一情況有了很大的改觀。Jdk1.5之後加入了java.util.concurrent包,這個包中主要介紹java Java併發包原始碼學習系列:阻塞佇列BlockingQueue及實現原理分析[toc] 系列傳送門: - [Java併發包原始碼學習系列:AbstractQueuedSynchronizer](https://blog.csdn.net/Sky_QiaoBa_Sum/article/details/112254373) - [Java併發包原始碼學習系列:CLH同步佇列及同步資源 |