Pratice Of Concurrency(一: BlockingQueue )
Java java.util.currency包中的BlockingQueue接口意味著線程可以在一個隊列中添加和提取對象.在接下來的段落中,我們將學習如何使用BlockingQueue接口.
BlockingQueue的使用
BlockingQueue典型應用是用于一個線程生產對象,另一個線程消費對象.
下面是一個原理描述圖:
一個阻塞隊列伴隨著一個線程往隊列中添加對象,另一個線程從隊列中提取對象.
生產線程負責生產新對象并發它添加進隊列中,直到達到隊列所能容納的邊界值為止.即達到容量限制.如果隊列達到容量限制,則生產線程在插入新對象時將會發生阻塞.直到有一個消費線程從隊列中取走一個對象為止.
消費線程負責從阻塞隊列中取出對象并處理它們.如果消費線程嘗試從空隊列中取出空隊列,那么消費線程將會阻塞直到生產線程往隊列中放入一個對象為止.
BlockingQueue方法
一個阻塞隊列包含四種截然不同的方法集,用于完成在隊列中插入,移除和檢查元素.每種集合的不同之處在于操作請求不能被立即執行時的不同行為.下面是這些方法的列表:
| Insert | add(o) | offer(o) | put(o) | offer(o, timeout, time unit) |
| Remove | remove(o) | poll() | take() | poll(timeout, timeunit) |
| Examine | element() | peek() |
四種不同的行為結合如下:
不能插入null到BlockingQueue中.如果你這么做了,BlockingQueue將拋出一個NullPointerException.
當然我們也能夠訪問BlockingQueue的所有元素, 不只是隊頭和隊尾. 例如, 你需要出隊一個對象用于執行,但你的應用決定取消它.那么你仍然可以使用類似remove(o)方法來移除隊列中指定的對象.然而這不是很高效,所以你不應該使用這類方法, 除非你真的需要這么做.
BlockingQueue的多種實現
BlockingQueue只是一個接口, 所以你需要使用它眾多實現的其中一種來使用它.java.util.concurrency包中有如下幾種BlockingQueue的接口實現(在Java6中):
- ArrayBlockingQueue
- DelayQueue
- LinkedBlockingQueue
- PriorityBlockingQueue
- SynchronousQueue
Java BlockingQueue實例
下面是一個Java BlockingQueue的實例. 實例中使用BlockingQueue接口的實現類,ArrayBlockingQueue.
首先,BlockingQueueExample類中分別啟動一個生產和消費線程.生產線程負責插入字符串到共享BlockingQueue中,而消費線程則負責取走它們.
public class ArrayBlockingQueueExample {public static void main(String[] args) {ArrayBlockingQueue<String> queue = new ArrayBlockingQueue<>(1024);Producer producer = new Producer(queue);Consumer consumer = new Consumer(queue);new Thread(producer).start();new Thread(consumer).start();try {Thread.sleep(4000);} catch (InterruptedException e) {e.printStackTrace();}} } 復制代碼下面是Producer類.注意我們每調用一次put()就會讓線程睡眠一秒.這會導致消費線程在隊列中等待對象時發生阻塞.
public class Producer implements Runnable {private ArrayBlockingQueue<String> queue;public Producer(ArrayBlockingQueue<String> queue) {this.queue = queue;}public void run() {try {queue.put("1");Thread.sleep(1000);queue.put("2");Thread.sleep(1000);queue.put("3");Thread.sleep(1000);} catch (InterruptedException e) {e.printStackTrace();}} } 復制代碼下面是Consumer類.它只是負責從隊列中取出字符串并通過System.out打印出來.
package org.menfre;import java.util.concurrent.ArrayBlockingQueue;public class Consumer implements Runnable {private ArrayBlockingQueue<String> queue;public Consumer(ArrayBlockingQueue<String> queue){this.queue = queue;}public void run() {try {System.out.println(queue.take());System.out.println(queue.take());System.out.println(queue.take());} catch (InterruptedException e) {e.printStackTrace();}} } 復制代碼該系列博文為筆者復習基礎所著譯文或理解后的產物,復習原文來自Jakob Jenkov所著Java.util.concurrent
Next: ArrayBlockingQueue
轉載于:https://juejin.im/post/5cf548aef265da1bb2771b0d
總結
以上是生活随笔為你收集整理的Pratice Of Concurrency(一: BlockingQueue )的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 质感设计 android,扣丁学堂And
- 下一篇: 数据仓库建设Best Pratice学习