ArrayBlockingQueue是JAVA5中的一個阻塞隊列,能夠自定義隊列大小,當插入時,如果隊列已經沒有空閑位置,那么新的插入線程將阻塞到該隊列,一旦該隊列有空閑位置,那么阻塞的線程將執行插入。從隊列中取數據為:take,放數據為:put。下面的例子模擬了兩個隊列的插入和獲取,首先在隊列2中插入一個數據,啟動線程2向隊列2中插入數據時,該線程將阻塞在隊列2等待,同時啟動線程1向隊列1中插入數據,由於隊列1此時為空那么能夠正確插入,然后從隊列2中取數據,當線程1再次插入時,阻塞到隊列1,此時,阻塞在隊列2的線程2能夠插入,並且從隊列1中取數據,此時線程1能夠插入,如此往復50次,並且每次插入成功后都循環輸出10次。代碼如下:
import java.util.concurrent.ArrayBlockingQueue; import java.util.concurrent.BlockingQueue; public class ArrayBlockingCommunication { public static void main(String[] args) { final Business business = new Business(); new Thread(new Runnable(){ public void run() { for(int i=0; i<50; i++){ business.sub(i); } } }).start(); new Thread(new Runnable(){ public void run() { for(int i=0; i<50; i++){ business.main(i); } } }).start(); } static class Business{ BlockingQueue<Integer> queue1 = new ArrayBlockingQueue<Integer>(1); BlockingQueue<Integer> queue2 = new ArrayBlockingQueue<Integer>(1); { try{ queue2.put(1); }catch(Exception e){ e.printStackTrace(); } } public void sub(int i){ try { queue1.put(1); System.out.println("線程" + Thread.currentThread().getName() + "正在阻塞"); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } System.out.println("線程" + Thread.currentThread().getName() + "開始運行"); for(int j=1; j<=10; j++){ System.out.println("sub thread sequence is " + j + " loop of " + i); } try { queue2.take(); } catch (InterruptedException e) { e.printStackTrace(); } } public void main(int i){ try { queue2.put(1); System.out.println("線程" + Thread.currentThread().getName() + "正在阻塞"); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("線程" + Thread.currentThread().getName() + "開始運行"); for(int j=1; j<=10; j++){ System.out.println("main thread sequence is " + j + " loop of " + i); } try { queue1.take(); } catch (InterruptedException e) { e.printStackTrace(); } } } }
請大家注意:在Business類中有一個匿名構造函數,其特點如下:
匿名構造方法,在任何構造方法之前被調用。這樣保證我們初始化Business類時已經向隊列2中插入了數據,這樣執行起來保證我們看到的線程1先運行,然后是線程2。