<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    xylz,imxylz

    關注后端架構、中間件、分布式和并發編程

       :: 首頁 :: 新隨筆 :: 聯系 :: 聚合  :: 管理 ::
      111 隨筆 :: 10 文章 :: 2680 評論 :: 0 Trackbacks

    這個小節介紹Queue的最后一個工具,也是最強大的一個工具。從名稱上就可以看到此工具的特點:雙向并發阻塞隊列。所謂雙向是指可以從隊列的頭和尾同時操作,并發只是線程安全的實現,阻塞允許在入隊出隊不滿足條件時掛起線程,這里說的隊列是指支持FIFO/FILO實現的鏈表。

     

    首先看下LinkedBlockingDeque的數據結構。通常情況下從數據結構上就能看出這種實現的優缺點,這樣就知道如何更好的使用工具了。

    LinkedBlockingDeque類圖

    從數據結構和功能需求上可以得到以下結論:

    1. 要想支持阻塞功能,隊列的容量一定是固定的,否則無法在入隊的時候掛起線程。也就是capacity是final類型的。
    2. 既然是雙向鏈表,每一個結點就需要前后兩個引用,這樣才能將所有元素串聯起來,支持雙向遍歷。也即需要prev/next兩個引用。
    3. 雙向鏈表需要頭尾同時操作,所以需要first/last兩個節點,當然可以參考LinkedList那樣采用一個節點的雙向來完成,那樣實現起來就稍微麻煩點。
    4. 既然要支持阻塞功能,就需要鎖和條件變量來掛起線程。這里使用一個鎖兩個條件變量來完成此功能。

     

    有了上面的結論再來研究LinkedBlockingDeque的優缺點。

    優點當然是功能足夠強大,同時由于采用一個獨占鎖,因此實現起來也比較簡單。所有對隊列的操作都加鎖就可以完成。同時獨占鎖也能夠很好的支持雙向阻塞的特性。

    凡事有利必有弊。缺點就是由于獨占鎖,所以不能同時進行兩個操作,這樣性能上就大打折扣。從性能的角度講LinkedBlockingDeque要比LinkedBlockingQueue要低很多,比CocurrentLinkedQueue就低更多了,這在高并發情況下就比較明顯了。

    前面分析足夠多的Queue實現后,LinkedBlockingDeque的原理和實現就不值得一提了,無非是在獨占鎖下對一個鏈表的普通操作。

    有趣的是此類支持序列化,但是Node并不支持序列化,因此fist/last就不能序列化,那么如何完成序列化/反序列化過程呢?

    清單1 LinkedBlockingDeque的序列化、反序列化

    private void writeObject(java.io.ObjectOutputStream s)
        throws java.io.IOException {
        lock.lock();
        try {
            // Write out capacity and any hidden stuff
            s.defaultWriteObject();
            // Write out all elements in the proper order.
            for (Node<E> p = first; p != null; p = p.next)
                s.writeObject(p.item);
            // Use trailing null as sentinel
            s.writeObject(null);
        } finally {
            lock.unlock();
        }
    }

    private void readObject(java.io.ObjectInputStream s)
        throws java.io.IOException, ClassNotFoundException {
        s.defaultReadObject();
        count = 0;
        first = null;
        last = null;
        // Read in all elements and place in queue
        for (;;) {
            E item = (E)s.readObject();
            if (item == null)
                break;
            add(item);
        }
    }

     

    清單1 描述的是LinkedBlockingDeque序列化/反序列化的過程。序列化時將真正的元素寫入輸出流,最后還寫入了一個null。讀取的時候將所有對象列表讀出來,如果讀取到一個null就表示結束。這就是為什么寫入的時候寫入一個null的原因,因為沒有將count寫入流,所以就靠null來表示結束,省一個整數空間。

     



    ©2009-2014 IMXYLZ |求賢若渴
    posted on 2010-08-18 16:01 imxylz 閱讀(9752) 評論(5)  編輯  收藏 所屬分類: Java Concurrency

    評論

    # re: 深入淺出 Java Concurrency (25): 并發容器 part 10 雙向并發阻塞隊列 BlockingDeque[未登錄] 2010-08-19 16:25 行云流水
    樓主走神了,這么久來更新一次。哈哈  回復  更多評論
      

    # re: 深入淺出 Java Concurrency (25): 并發容器 part 10 雙向并發阻塞隊列 BlockingDeque[未登錄] 2010-11-16 16:38 蟲蟲
    樓主怎么不繼續拉,想看啊~  回復  更多評論
      

    # re: 深入淺出 Java Concurrency (25): 并發容器 part 10 雙向并發阻塞隊列 BlockingDeque 2011-02-15 10:46 hixiaomin
    最底部導航有些小問題,哈哈。  回復  更多評論
      

    # re: 深入淺出 Java Concurrency (25): 并發容器 part 10 雙向并發阻塞隊列 BlockingDeque 2011-02-15 10:51 xylz
    @hixiaomin
    你真仔細,贊!  回復  更多評論
      

    # re: 深入淺出 Java Concurrency (25): 并發容器 part 10 雙向并發阻塞隊列 BlockingDeque[未登錄] 2016-04-22 15:19
    Mark,今天看到這里啦,滿滿的成就感。。。。。嘿嘿  回復  更多評論
      


    ©2009-2014 IMXYLZ
    主站蜘蛛池模板: 免费在线精品视频| 麻豆国产精品入口免费观看| 国产亚洲av片在线观看播放| 国产精品偷伦视频免费观看了| 免费夜色污私人影院在线观看| 青草青草视频2免费观看| 亚洲AV日韩精品一区二区三区| 女人裸身j部免费视频无遮挡| 亚洲国产精品第一区二区三区| 亚洲精品国产日韩无码AV永久免费网| 久久久久噜噜噜亚洲熟女综合 | 亚洲国产精华液网站w| 国产真人无码作爱免费视频| 亚洲精品乱码久久久久久久久久久久| 久久青草国产免费观看| 亚洲综合无码一区二区三区| 成人性生交视频免费观看| 亚洲欧美在线x视频| 亚洲免费一区二区| 男人j进入女人j内部免费网站| 亚洲综合无码一区二区三区| 成人免费视频一区二区三区| 羞羞漫画在线成人漫画阅读免费| 丁香五月亚洲综合深深爱| 91成人在线免费视频| 亚洲综合无码一区二区痴汉| 亚洲日本在线观看视频| 久久久久久久久久国产精品免费| 456亚洲人成影院在线观| 亚洲高清国产拍精品青青草原| 国产白丝无码免费视频| 国产精品亚洲午夜一区二区三区| 国产免费av一区二区三区| 三年片免费观看大全国语| 亚洲人成激情在线播放| 免费在线观看a级毛片| 无码人妻精品中文字幕免费| 亚洲AV永久无码天堂影院| 亚洲热妇无码AV在线播放| 毛片免费在线播放| 三级网站免费观看|