首页 > 代码库 > 多线程之阻塞队列ArrayBlockingQueue,BlockingQueue
多线程之阻塞队列ArrayBlockingQueue,BlockingQueue
ArrayBlockingQueue是个有数组支持的有界的阻塞队列。该队列按照先进先出FIFO的原理对元素排序,插入新元素市场队列的尾部,获取新元素是操作队列的开始处。一旦见了建立了缓存区,就不能再增加其容量,试图从已满的队列中方式元素会导致操作阻塞;试图从空的队列中提取元素将导致阻塞。
提拱了四种方法,只有put(),take()才会发生阻塞。
下面是阻塞队列的例子。
package andy.thread.test; import java.util.concurrent.ArrayBlockingQueue; import java.util.concurrent.BlockingQueue; /** * @author Zhang,Tianyou * @version 2014年11月9日 下午5:29:28 */ public class BlockingQueueTest { public static void main(String[] args) { final int CAPACITY = 3; BlockingQueue<Integer> queue = new ArrayBlockingQueue<Integer>(CAPACITY); for (int i = 0; i < 2; i++) { new Thread() { public void run() { while (true) { try { Thread.sleep((long) (Math.random() * 1000)); System.out.println(Thread.currentThread().getName() + "准备放数据!"); queue.put(1); System.out.println(Thread.currentThread().getName() + "已经放了数据," + "队列目前有" + queue.size() + "个数据"); } catch (InterruptedException e) { e.printStackTrace(); } } } }.start(); } new Thread() { public void run() { while (true) { try { // 将此处的睡眠时间分别改为100和1000,观察运行结果 Thread.sleep(1000); System.out.println(Thread.currentThread().getName() + "准备取数据!"); queue.take(); System.out.println(Thread.currentThread().getName() + "已经取走数据," + "队列目前有" + queue.size() + "个数据"); } catch (InterruptedException e) { e.printStackTrace(); } } } }.start(); } }
Thread-0准备放数据!
Thread-0已经放了数据,队列目前有1个数据
Thread-1准备放数据!
Thread-1已经放了数据,队列目前有2个数据
Thread-0准备放数据!
Thread-0已经放了数据,队列目前有3个数据
Thread-1准备放数据!
Thread-0准备放数据!
Thread-2准备取数据!
Thread-2已经取走数据,队列目前有2个数据
Thread-1已经放了数据,队列目前有3个数据
2、 可以使用阻塞队列完成两个线程循环交替打印。
我们需要定义两个大小唯一的阻塞队列,当一个线程执行时,给另一个队列里存一个值,让另一个线程处于阻塞状态;当前线程执行完毕时,将另一个阻塞队列取出值,让对应的线程执行。
实例如下:
package andy.thread.test; import java.util.concurrent.ArrayBlockingQueue; import java.util.concurrent.BlockingQueue; /** * @author Zhang,Tianyou * @version 2014年11月9日 下午5:43:28 */ public class BlockingQueueCommunication { public static void main(String[] args) { A a = new A(); new Thread(new Runnable() { @Override public void run() { for (int i = 1; i <= 3; i++) { a.sub(i); } } }).start(); for (int i = 1; i <= 3; i++) { a.main(i); } } static class A { BlockingQueue<Integer> mainQueue = new ArrayBlockingQueue<Integer>(1); BlockingQueue<Integer> subQueue = new ArrayBlockingQueue<Integer>(1); // 定义一个匿名构造函数 匿名构造函数在所有的构造函数前开始执行 new多少个实例执行多少次 // static 是在JVM加载时执行 执行一次 { try { subQueue.put(1);// 阻塞子线程 先让第主线程执行 } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } public void sub(int i) { try { // 阻塞主线程 subQueue.put(1); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } System.out.println("sub thread task is " + i); try { mainQueue.take(); // 子线程执行完 让改主线程执行 } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } public void main(int i) { try { // 阻塞主线程 mainQueue.put(1); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } System.out.println("main thread task is " + i); try { subQueue.take(); // 子线程执行完 让改主线程执行 } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } }
运行效果如下
main thread task is 1
sub thread task is 1
main thread task is 2
sub thread task is 2
main thread task is 3
sub thread task is 3
多线程之阻塞队列ArrayBlockingQueue,BlockingQueue
声明:以上内容来自用户投稿及互联网公开渠道收集整理发布,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任,若内容有误或涉及侵权可进行投诉: 投诉/举报 工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。