国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 編程 > Java > 正文

線程小酌之JAVA中的阻塞隊列

2019-11-11 06:02:42
字體:
來源:轉載
供稿:網友

       最近在學習java中自帶的JDK并發包,java.util.concurrent,發現功能很強大,其中之一就是工作中多次用到的線程工具類BlockingQueue。在實際開發工作和面試過程中,經常會考察對于該工具類的使用和理解。

1. 什么是阻塞隊列?

阻塞隊列(BlockingQueue)是一個支持兩個附加操作的隊列。這兩個附加的操作是:在隊列為空時,獲取元素的線程會等待隊列變為非空。當隊列滿時,存儲元素的線程會等待隊列可用。阻塞隊列常用于生產者和消費者的場景,生產者是往隊列里添加元素的線程,消費者是從隊列里拿元素的線程。阻塞隊列就是生產者存放元素的容器,而消費者也只從容器里拿元素。

2.詳解BlockingQueue

BlockingQueue最終會有四種狀況,拋出異常、返回特殊值、阻塞、超時,下表總結了這些方法:

 拋出異常特殊值阻塞超時
插入add(e)offer(e)put(e)offer(e, time, unit)
移除remove()poll()take()poll(time, unit)
檢查element()peek()不可用不可用

       BlockingQueue是個接口,有如下實現類:

       1. ArrayBlockQueue:一個由數組支持的有界阻塞隊列。此隊列按 FIFO(先進先出)原則對元素進行排序。創建其對象必須明確大小,像數組一樣。

       2. LinkedBlockQueue:一個可改變大小的阻塞隊列。此隊列按 FIFO(先進先出)原則對元素進行排序。創建其對象如果沒有明確大小,默認值是Integer.MAX_VALUE。鏈接隊列的吞吐量通常要高于基于數組的隊列,但是在大多數并發應用程序中,其可預知的性能要低。 

       3. PRiorityBlockingQueue:類似于LinkedBlockingQueue,但其所含對象的排序不是FIFO,而是依據對象的自然排序順序或者是構造函數所帶的Comparator決定的順序。

       4. SynchronousQueue:同步隊列。同步隊列沒有任何容量,每個插入必須等待另一個線程移除,反之亦然。

由于LinkedBlockingQueue實現是線程安全的,實現了先進先出等特性,是作為生產者消費者的首選,LinkedBlockingQueue 可以指定容量,也可以不指定,不指定的話,默認最大是Integer.MAX_VALUE,其中主要用到put和take方法,put方法在隊列滿的時候會阻塞直到有隊列成員被消費,take方法在隊列空的時候會阻塞,直到有隊列成員被放進來。

package cn.thread;import java.util.concurrent.BlockingQueue;import java.util.concurrent.ExecutorService;import java.util.concurrent.Executors;import java.util.concurrent.LinkedBlockingQueue;/** * 多線程模擬實現生產者/消費者模型 *   */public class BlockingQueueTest2 {    /**     *      * 定義裝蘋果的籃子     *      */    public class Basket {        // 籃子,能夠容納3個蘋果        BlockingQueue<String> basket = new LinkedBlockingQueue<String>(3);        // 生產蘋果,放入籃子        public void produce() throws InterruptedException {            // put方法放入一個蘋果,若basket滿了,等到basket有位置            basket.put("An apple");        }        // 消費蘋果,從籃子中取走        public String consume() throws InterruptedException {            // take方法取出一個蘋果,若basket為空,等到basket有蘋果為止(獲取并移除此隊列的頭部)            return basket.take();        }    }    // 定義蘋果生產者    class Producer implements Runnable {        private String instance;        private Basket basket;        public Producer(String instance, Basket basket) {            this.instance = instance;            this.basket = basket;        }        public void run() {            try {                while (true) {                    // 生產蘋果                    System.out.println("生產者準備生產蘋果:" + instance);                    basket.produce();                    System.out.println("!生產者生產蘋果完畢:" + instance);                    // 休眠300ms                    Thread.sleep(300);                }            } catch (InterruptedException ex) {                System.out.println("Producer Interrupted");            }        }    }    // 定義蘋果消費者    class Consumer implements Runnable {        private String instance;        private Basket basket;        public Consumer(String instance, Basket basket) {            this.instance = instance;            this.basket = basket;        }        public void run() {            try {                while (true) {                    // 消費蘋果                    System.out.println("消費者準備消費蘋果:" + instance);                    System.out.println(basket.consume());                    System.out.println("!消費者消費蘋果完畢:" + instance);                    // 休眠1000ms                    Thread.sleep(1000);                }            } catch (InterruptedException ex) {                System.out.println("Consumer Interrupted");            }        }    }    public static void main(String[] args) {        BlockingQueueTest2 test = new BlockingQueueTest2();        // 建立一個裝蘋果的籃子        Basket basket = test.new Basket();        ExecutorService service = Executors.newCachedThreadPool();        Producer producer = test.new Producer("生產者001", basket);        Producer producer2 = test.new Producer("生產者002", basket);        Consumer consumer = test.new Consumer("消費者001", basket);        service.submit(producer);        service.submit(producer2);        service.submit(consumer);        // 程序運行5s后,所有任務停止//        try {//            Thread.sleep(1000 * 5);//        } catch (InterruptedException e) {//            e.printStackTrace();//        }//        service.shutdownNow();    }}


發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 晋江市| 溧阳市| 白沙| 驻马店市| 黄浦区| 介休市| 侯马市| 大同市| 马龙县| 梨树县| 德州市| 荆门市| 沙洋县| 宁波市| 安乡县| 株洲市| 松阳县| 曲阳县| 定安县| 白城市| 江永县| 奇台县| 祁东县| 馆陶县| 宝丰县| 乌鲁木齐县| 临沭县| 东方市| 金堂县| 安西县| 富锦市| 巢湖市| 顺昌县| 东山县| 曲阳县| 即墨市| 天津市| 孟州市| 宾川县| 永济市| 沙湾县|