1、有界缓存的基类

package cn.xf.cp.ch14;

/**
*
*功能:有界缓存实现基类
*时间:下午2:20:00
*文件:BaseBoundedBuffer.java
*@author Administrator
*
* @param <V>
*/
public class BaseBoundedBuffer<V>
{
private final V[] buf;
private int tail;
private int head;
private int count; public BaseBoundedBuffer(int capacity)
{
//初始化数组
this.buf = (V[]) new Object[capacity];
} //放入一个数据,final方法无法被重写
protected synchronized final void doPut(V v)
{
buf[tail] = v;
if(++tail == buf.length)
{
tail = 0;
}
//插入一个方法,总量++
++count;
} /**
* 取出一个数据
* @return
*/
protected synchronized final V doTake()
{
V v = buf[head];
buf[head] = null;
if(++head == buf.length)
{
head = 0;
}
--count;
return v;
} //通过对count的判断,来确定数组是否是满的
public synchronized final boolean isFull()
{
return count == buf.length;
} public synchronized final boolean isEmpty()
{
return count == 0;
}
}

2、判定前提条件再执行操作

package cn.xf.cp.ch14;

/**
*
*功能:对插入和获取元素操作进行先行检查,然后执行操作,校验不通过不予操作
*时间:下午2:33:41
*文件:GrumpyBoundedBuffer.java
*@author Administrator
*
* @param <V>
*/
public class GrumpyBoundedBuffer<V> extends BaseBoundedBuffer<V>
{ public GrumpyBoundedBuffer(int size)
{
super(size);
} public synchronized void put(V v) throws Exception
{
//如果是满的队列,就无法插入新的元素
if(this.isFull())
{
throw new Exception("队列超出");
}
this.doPut(v);
} //同理,队列为空的就无法取出新的元素
public synchronized V take() throws Exception
{
if(this.isEmpty())
{
throw new Exception("队列中无元素");
} return this.doTake();
} }

3、通过轮询与休眠来实现简单的阻塞

package cn.xf.cp.ch14;

/**
*
*功能:通过轮询与休眠来实现简单的阻塞
*时间:下午2:55:54
*文件:SleepyBoundedBuffer.java
*@author Administrator
*
* @param <V>
*/
public class SleepyBoundedBuffer<V> extends BaseBoundedBuffer<V>
{
//2s
private static final long SLEEP_GRANULARITY = 2000; public SleepyBoundedBuffer(int capacity)
{
super(capacity);
} //放入队列的时候
public void put(V v) throws InterruptedException
{
while(true)
{
//这里不对循环上锁,不然这个锁就无法释放了,不对休眠上锁,休眠上锁,在休眠的时候别人也无法操作,永远都不可能有元素出去
synchronized (this)
{
//如果队列不是满的,那么就放入元素
if(!this.isFull())
{
this.doPut(v);
return;
}
}
//否则休眠,退出cpu占用
Thread.sleep(SLEEP_GRANULARITY);
}
} public V take() throws InterruptedException
{
while(true)
{
//这里不对循环上锁,不然这个锁就无法释放了,不对休眠上锁,休眠上锁,在休眠的时候别人也无法操作,永远都不可能有新的元素进来
synchronized(this)
{
//如果数组部位空,那么就可以取出数据
if(!this.isEmpty())
{
return this.doTake();
}
//如果队列为空,休眠几秒再试
}
Thread.sleep(SLEEP_GRANULARITY);
}
} }

4、条件队列

package cn.xf.cp.ch14;

/**
*
*功能:使用条件队列
*时间:下午3:32:04
*文件:BoundedBuffer.java
*@author Administrator
*
* @param <V>
*/
public class BoundedBuffer<V> extends BaseBoundedBuffer<V>
{ public BoundedBuffer(int capacity)
{
super(capacity);
} /**
* 放入数据元素
* @param v
* @throws InterruptedException
*/
public synchronized void put(V v) throws InterruptedException
{
while(this.isFull())
{
//这里挂起程序,会释放锁
this.wait();
}
//如果队列不为满的,那么程序被唤醒之后从新获取锁
this.doPut(v);
//执行结束,唤醒其他队列
this.notifyAll();
} public synchronized V take() throws InterruptedException
{
while(this.isEmpty())
{
this.wait();
}
V v = this.doTake();
this.notifyAll();
return v;
} }

【JAVA并发编程实战】11、有界缓存的实现的更多相关文章

  1. java并发编程实战学习(3)--基础构建模块

    转自:java并发编程实战 5.3阻塞队列和生产者-消费者模式 BlockingQueue阻塞队列提供可阻塞的put和take方法,以及支持定时的offer和poll方法.如果队列已经满了,那么put ...

  2. 《Java并发编程实战》/童云兰译【PDF】下载

    <Java并发编程实战>/童云兰译[PDF]下载链接: https://u253469.pipipan.com/fs/253469-230062521 内容简介 本书深入浅出地介绍了Jav ...

  3. java并发编程实战《二》java内存模型

    Java解决可见性和有序性问题:Java内存模型 什么是 Java 内存模型? Java 内存模型是个很复杂的规范,可以从不同的视角来解读,站在我们这些程序员的视角,本质上可以理解为, Java 内存 ...

  4. 【Java并发编程实战】-----“J.U.C”:ReentrantReadWriteLock

    ReentrantLock实现了标准的互斥操作,也就是说在某一时刻只有有一个线程持有锁.ReentrantLock采用这种独占的保守锁直接,在一定程度上减低了吞吐量.在这种情况下任何的"读/ ...

  5. 【Java并发编程实战】-----“J.U.C”:Semaphore

    信号量Semaphore是一个控制访问多个共享资源的计数器,它本质上是一个"共享锁". Java并发提供了两种加锁模式:共享锁和独占锁.前面LZ介绍的ReentrantLock就是 ...

  6. Java并发编程实战---第六章:任务执行

    废话开篇 今天开始学习Java并发编程实战,很多大牛都推荐,所以为了能在并发编程的道路上留下点书本上的知识,所以也就有了这篇博文.今天主要学习的是任务执行章节,主要讲了任务执行定义.Executor. ...

  7. 那些年读过的书《Java并发编程实战》和《Java并发编程的艺术》三、任务执行框架—Executor框架小结

    <Java并发编程实战>和<Java并发编程的艺术>           Executor框架小结 1.在线程中如何执行任务 (1)任务执行目标: 在正常负载情况下,服务器应用 ...

  8. 《Java并发编程实战》文摘

    更新时间:2017-06-03 <Java并发编程实战>文摘,有兴趣的朋友可以买本纸质书仔细研究下. 一 线程安全性 1.1 什么是线程安全性 当多个线程访问某个类时,不管运行时环境采用何 ...

  9. Java并发编程实战 01并发编程的Bug源头

    摘要 编写正确的并发程序对我来说是一件极其困难的事情,由于知识不足,只知道synchronized这个修饰符进行同步. 本文为学习极客时间:Java并发编程实战 01的总结,文章取图也是来自于该文章 ...

  10. Java并发编程实战 02Java如何解决可见性和有序性问题

    摘要 在上一篇文章当中,讲到了CPU缓存导致可见性.线程切换导致了原子性.编译优化导致了有序性问题.那么这篇文章就先解决其中的可见性和有序性问题,引出了今天的主角:Java内存模型(面试并发的时候会经 ...

随机推荐

  1. IM消息送达保证机制实现(二):保证离线消息的可靠投递

    1.前言 本文的上篇<IM消息送达保证机制实现(一):保证在线实时消息的可靠投递>中,我们讨论了在线实时消息的投递可以通过应用层的确认.发送方的超时重传.接收方的去重等手段来保证业务层面消 ...

  2. memset

    函数原型: void *memset(void *s, int ch, size_t n); 函数解释:将s中当前位置后面的n个字节 (typedef unsigned int size_t )用 c ...

  3. 重温 w3cshool css3

    border-radius: 2em 1em 4em / 0.5em 3em;  兼容性IE9+.Firefox 4+.Chrome.Safari 5+ 以及 Opera 支持 border-radi ...

  4. php 操作数组(合并,拆分,追加,查找,删除等)(转载)

    1. 合并数组 array_merge()函数将数组合并到一起,返回一个联合的数组.所得到的数组以第一个输入数组参数开始,按后面数组参数出现的顺序依次迫加.其形式为: array array_merg ...

  5. Enterprise Solution 虚拟测试环境

    在不联网的情况下,一台物理电脑安装数据库服务,VMware创建多个虚拟机,虚拟机中多个客户端并发连接到物理主机.可共用同一个物理主机的数据库,也可以测试多用户并发等问题. 1  安装微软虚拟网卡.在控 ...

  6. ExecuteReader在执行有输出参数的存储过程时拿不到输出参数

    异常处理汇总-后端系列 http://www.cnblogs.com/dunitian/p/4523006.html 后期会在博客首发更新:http://dnt.dkill.net/Article/D ...

  7. 【解决】Word 在试图打开文件时遇到错误 请尝试下列方法:* xxx * xxx * xxx

    有好几种情况,我先说我的这个情况 1.word设置不当导致 看图: 然后就能打开了~ 2.word格式问题,比如原来是doc,被人手动改成docx~~~ 解决方法:改回来 3.word版本不兼容,比如 ...

  8. Android中activity背景色的设置

    Android应用开发——系统自带样式Android:theme •android:theme="@android:style/Theme.Dialog"   将一个Activit ...

  9. Codeforces Round #323 (Div. 2) C.GCD Table

    C. GCD Table The GCD table G of size n × n for an array of positive integers a of length n is define ...

  10. node-mysql 在4.2.0的时候遇到的错误

    实际上这个问题折腾了几天.前一阵因为升级到了最新的4.2.0,发现mysql的应用就出错了,错误消息也比较奇怪 Handshake Inactivity Timeout - PROTOCOL_SEQU ...