java并发编程条件队列的唤醒机制探究
来源:互联网 发布:中国儿童编程网 编辑:程序博客网 时间:2024/05/22 14:08
bf1,bf2是两个大小各为3的条件队列。3将要put进bf1,此时因为bf1已满而已调用wait()方法挂起线程,此时若对bf2()执行take()方法并调用notifyall()是否会唤醒wait()中的bf1?(对两个队列的操作存在于两个不同的线程中)
先上代码
public abstract class BaseBoundedBuffer<V>{ private final V[] buf; private int tail; private int head; private int count; protected BaseBoundedBuffer(int capacity) { this.buf = (V[]) new Object[capacity]; } protected synchronized final void doPut(V v){ buf[tail]=v; if (++tail==buf.length){ tail=0; } ++count; } protected synchronized final V doTake(){ V v=buf[head]; buf[head]=null; if (++head == buf.length){ head=0; } --count; return v; } public synchronized final boolean isFull(){ return count==buf.length; } public synchronized final boolean isEmpty(){ return count==0; }}
public class BoundedBuffer<V> extends BaseBoundedBuffer { private int id; protected BoundedBuffer(int capacity,int id) { super(capacity); this.id=id; } public synchronized void put(V v)throws InterruptedException{ //对条件队列执行增加元素的操作 while (isFull()){ System.out.println(id+"快睡了------put"); wait(); System.out.println(id+"醒了--------put"); } doPut(v); System.out.println(id+"put"+v); notifyAll(); } public synchronized V take() throws InterruptedException{ //对条件队列执行读取操作 while (isEmpty()){ System.out.println(id+"快睡了--------take"); wait(); System.out.println(id+"醒了----------take"); } V v= (V) doTake(); notifyAll(); return v; }}
public class BufferTest { public static void main(String[] args) throws InterruptedException { BoundedBuffer bf =new BoundedBuffer(3,1); BoundedBuffer bf2=new BoundedBuffer(3,2); bf2.put(9999999); new Thread(){ public void run(){ for (int i=0;i<4;i++){ try { bf.put(i); } catch (InterruptedException e) { e.printStackTrace(); } } } }.start(); new Thread(){ public void run(){ try { System.out.println( bf2.take()); } catch (InterruptedException e) { e.printStackTrace(); } } }.start(); }}
执行结果如下2put99999991put01put11put21快睡了------put9999999
在执行结果第五行的时候便是上图所描述的情况(3想要put进bf1,但是因为已经full,bf1进入wait()状态),第六行输出了9999999,也就说明bf2执行了take()操作,同时也执行了notifyAll()方法,然而对bf1没有产生任何影响。 V v= (V) doTake();
notifyAll();
return v;
结果证明: 在使用条件队列时候,notifyAll()只会唤醒同一对象因执行wait()被挂起的线程
阅读全文
0 0
- java并发编程条件队列的唤醒机制探究
- JAVA并发-条件队列
- 并发学习之:多线程编程中条件变量和虚假唤醒的讨论
- 【并发】多线程编程中条件变量和虚假唤醒的讨论
- 并发学习之:多线程编程中条件变量和虚假唤醒的讨论
- Java并发编程(二)线程同步和等待唤醒机制
- java并发编程:线程等待与唤醒
- Java多线程的唤醒机制
- Java并发:线程间同步机制:条件队列和同步工具类
- Java并发编程-并发队列(ConcurrentLinkedQueue)的原理分析
- Java并发编程-并发队列(ConcurrentLinkedQueue)的原理分析
- Java并发编程系列之一:并发机制的底层原理
- Java并发编程系列之一:并发机制的底层原理
- Java并发编程:阻塞队列
- Java并发编程:阻塞队列
- Java并发编程:阻塞队列
- Java并发编程:阻塞队列
- Java并发编程:阻塞队列
- 学习html
- ArrayList循环遍历并删除元素的常见陷阱
- 1分钟搭建完整laravel后台
- C语言通讯录(利用链表实现)
- 关于static关键字的一些学习
- java并发编程条件队列的唤醒机制探究
- HDU 5672 String
- day5模块学习--hashlib模块
- MpAndroidChart绘制折线图及标志线
- HTTP 请求方式: GET和POST的比较
- C++ Windows Server 2016用CMD命令行安装IIS角色和功能组件
- 3.13—字符串—Anagrams
- Java 集合系列02之 Collection架构
- Liunx 常用命令(一)