彩虹天堂
          技術源于生活
          posts - 0,  comments - 2,  trackbacks - 0
          BlockingQueue

          佇列(Queue)是個先前先出(First In First Out, FIFO)的資料結構。在JDK 5.0中新增了Blocking Queue,在多執行緒的情況下,如果Blocking Queue的內容為空,而有個執行緒試圖從Queue中取出元素,則該執行緒會被Block,直到Queue有元素時才解除Block,反過來說,如果 Blocking Queue滿了,而有個執行緒試圖再把資料填入Queue中,則該執行緒會被Block,直到Queue中有元素被取走後解除Block。

          BlockingQueue的幾個主要操作為下:

          方法 說明
          add 加入元素,如果佇列是滿的,則丟出IllegalStateException
          remove 傳回並從佇列移除元素,如果佇列是空的,則丟出NoSuchElementException
          element 傳回元素,如果佇列是空的,則丟出NoSuchElementException
          offer 加入元素並傳回true,如果佇列是滿的,則傳回false
          poll 傳回並從佇列移除元素,如果佇列是空的,則傳回null
          peek 傳回元素,如果佇列是空的,則傳回null
          put 加入元素,如果佇列是滿,就block
          take 傳回並移除元素,如果佇列是空的,就block

          java.util.concurrent下提供幾種不同的Blocking Queue,ArrayBlockingQueue要指定容量大小來建構,LinkedBlockingQueue預設沒有容量上限,但也可以指定容量上限,PriorityBlockingQueue嚴格來說不是Queue,因為它是根據優先權(Priority)來移除元素。

          在這邊以 wait()、notify() 中的生產者、消費者程式為例,使用BlockQueue來加以改寫,好處是我們不用親自處理wait、notify的細節,首先生產者改寫如下:

          • Producer.java
          package onlyfun.caterpillar;

          import java.util.concurrent.BlockingQueue;

          public class Producer implements Runnable {
          private BlockingQueue<Integer> queue;

          public Producer(BlockingQueue<Integer> queue) {
          this.queue = queue;
          }

          public void run() {
          for(int product = 1; product <= 10; product++) {
          try {
          // wait for a random time
          Thread.sleep((int) Math.random() * 3000);
          queue.put(product);
          }
          catch(InterruptedException e) {
          e.printStackTrace();
          }
          }
          }
          }

          消費者類別改寫如下:
          • Consumer.java
          package onlyfun.caterpillar;

          import java.util.concurrent.BlockingQueue;

          public class Consumer implements Runnable {
          private BlockingQueue<Integer> queue;

          public Consumer(BlockingQueue<Integer> queue) {
          this.queue = queue;
          }

          public void run() {
          for(int i = 1; i <= 10; i++) {
          try {
          // wait for a random time
          Thread.sleep((int) (Math.random() * 3000));
          queue.take();
          }
          catch(InterruptedException e) {
          e.printStackTrace();
          }
          }
          }
          }

          可以使用下面這個程式來簡單的測試一下:
          • BlockingQueueDemo.java
          package onlyfun.caterpillar;

          import java.util.concurrent.ArrayBlockingQueue;
          import java.util.concurrent.BlockingQueue;

          public class BlockingQueueDemo {
          public static void main(String[] args) {
          BlockingQueue<Integer> queue = new ArrayBlockingQueue<Integer>(1);

          Thread producerThread = new Thread(
          new Producer(queue));
          Thread consumerThread = new Thread(
          new Consumer(queue));

          producerThread.start();
          consumerThread.start();
          }
          }
          posted on 2008-08-05 09:01 bcterry 閱讀(173) 評論(0)  編輯  收藏

          只有注冊用戶登錄后才能發表評論。


          網站導航:
           

          <2025年7月>
          293012345
          6789101112
          13141516171819
          20212223242526
          272829303112
          3456789

          留言簿

          文章檔案

          搜索

          •  

          最新評論

          主站蜘蛛池模板: 加查县| 宝鸡市| 龙胜| 乌拉特前旗| 高阳县| 油尖旺区| 遂溪县| 肥西县| 綦江县| 沁源县| 绥宁县| 吴旗县| 香河县| 阿拉善右旗| 施甸县| 洛扎县| 建宁县| 新乡市| 九龙坡区| 自贡市| 聊城市| 龙口市| 郎溪县| 阿尔山市| 黔东| 剑阁县| 海城市| 云南省| 临江市| 红原县| 天津市| 丰顺县| 和林格尔县| 湟中县| 漠河县| 攀枝花市| 通州区| 根河市| 闸北区| 吉安县| 夏邑县|