Guarded Suspension设计模式
Guarded Suspension 设计模式可以保证,当线程在访问某个对象时,发现条件不满足,就挂起等待条件满足时再次访问
public class GuardedSuspensionQueue {
// 定义存放Integer类型的queue
private final LinkedList<String> queue = new LinkedList<String>();
// 定义queue的最大容量为5
private final int LIMIT = ;
public static final Random random = new Random(System.currentTimeMillis());
// 往queue中插入数据,如果queue中的元素超过了最大容量,则会陷入阻塞
public void offer(String data) {
synchronized (this) {
// 判断queue的当前元素是否超过了LIMIT
while (queue.size() >= LIMIT) {
// 挂起当前线程,使其陷入阻塞
System.out.println("向queue中添加元素,元素个数超过了限制,"+Thread.currentThread().getName()+"被挂起!");
try {
this.wait();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
// 插入元素并且唤醒take线程
queue.addLast(data);
this.notifyAll();
}
}
// 从队列中获取元素,如果队列此时为空,则会使当前线程阻塞
public String take() {
synchronized (this) {
// 判断如果队列为空
while (queue.isEmpty()) {
// 则挂起当前线程
System.out.println(Thread.currentThread().getName()+"从queue中取出元素,元素个数为0,被挂起!");
try {
this.wait();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
return null;
}
}
//removeFirst不会返回null值,queue没有元素会抛出异常
String res = queue.removeFirst();
// 通知offer线程可以继续插入数据了
this.notifyAll();
return res;
}
}
public static void main(String[] args) throws InterruptedException {
GuardedSuspensionQueue queue = new GuardedSuspensionQueue();
TakerThread takerThread = new TakerThread(queue,"【线程A】");
takerThread.start();
Thread.sleep();
// 创建3个生产线程向queue中添加数据
IntStream.rangeClosed(, ).forEach(i -> {
new Thread(() -> {
for (int j = ; j <= ; j++) {
queue.offer("【线程"+i+"】放入的"+j);
}
try {
Thread.sleep(random.nextInt());
} catch (InterruptedException e) {
e.printStackTrace();
}
}).start();
});
Thread.sleep(10_000);
takerThread.close();
}
}
class TakerThread extends Thread{
private volatile boolean close = false;
private GuardedSuspensionQueue queue ;
TakerThread(GuardedSuspensionQueue queue,String name){
this.queue = queue;
setName(name);
}
@Override
public void run() {
while(!close) {
String item = queue.take();
if(item == null) {
break;
}
System.out.println(Thread.currentThread().getName() + "从queue中取出数据:" + item);
try {
Thread.sleep(GuardedSuspensionQueue.random.nextInt());
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
break;
}
}
}
public void close() {
this.close = close;
this.interrupt();
}
}
Guarded Suspension设计模式的更多相关文章
- 并发设计模式之Guarded Suspension模式
- 原文链接: http://www.joyhwong.com/2016/11/19/并发设计模式之guarded-suspension模式/ Guarded Suspension意为保护暂停,其核心 ...
- 多线程程序设计学习(4)guarded suspension模式
Guarded Suspension[生产消费者模式] 一:guarded suspension的参与者--->guardedObject(被防卫)参与者 1.1该 ...
- 多线程同步循环打印和Guarded suspension 模式
* 迅雷笔试题: * 有三个线程ID分别是A.B.C,请有多线编程实现,在屏幕上循环打印10次ABCABC… 由于线程执行的不确定性,要保证这样有序的输出,必须控制好多线程的同步. 线程同步有两种 ...
- 多线程学习之三生产者消费者模式Guarded Suspension
Guarded Suspension[生产消费者模式] 一:guarded suspension的参与者--->guardedObject(被防卫)参与者 1.1该 ...
- 多线程系列之四:Guarded Suspension 模式
一,什么是Guarded Suspension模式如果执行现在的处理会造成问题,就让执行处理的线程等待.这种模式通过让线程等待来保证实例的安全性 二,实现一个简单的线程间通信的例子 一个线程(Clie ...
- 并行模式之Guarded Suspension模式
并行模式之Guarded Suspension模式 一).Guarded Suspension: 保护暂存模式 应用场景:当多个客户进程去请求服务进程时,客户进程的请求速度比服务进程处里请求的速度快, ...
- Guarded Suspension Pattern【其他模式】
Guarded Suspension Pattern public class GuardedSuspension { /** * Guarded Suspension Pattern[保护悬挂模式] ...
- Guarded Suspension模式简单实现
Guarded Suspension 意为保护暂停,假设服务器很短时间内承受大量的客户端请求,客户端请求的数量超过服务器本身的即时处理能力,而服务器又不能丢弃任何一个客户端请求,此时可以让客户端的请求 ...
- 多线程编程-设计模式之保护性暂挂(Guarded Suspesion)模式
Guarded Suspension模式的架构 核心是一个受保护方法(Guarded Method).该方法需要执行其所要真正执行的操作时需要满足特定的条件(Predicate,以下称之为保护条件). ...
随机推荐
- Linux入门——注意事项
Linux入门——注意事项 摘要:本文主要说明了在使用Linux操作系统时,需要注意的问题. 严格区分大小写 和Windows不同,Linux是严格区分大小写的,包括文件名和目录名.命令.命令选项.配 ...
- AES加解密异常java.security.InvalidKeyException: Illegal key size
AES加解密异常 Java后台AES解密,抛出异常如下:java.security.InvalidKeyException: Illegal key size Illegal key size or ...
- Django的路由系统:URL
一. URLconf配置 基本格式 from django.conf.urls import url urlpatterns = [ url(正则表达式, views视图,参数,别名), ] 参数说明 ...
- 基于JQuery可拖动列表格插件DataTables的踩坑记
前言 最近项目中在使用能够拖动列调整列位置顺序的表格插件---DataTables,这也是目前我找到的唯一一种存在有这种功能的插件. 在查找使用方法的过程中发现可用案例并不多,且大多言语不详.本文将全 ...
- sparkSQL中的example学习(2)
UserDefinedUntypedAggregate.scala(默认返回类型为空,不能更改) import org.apache.spark.sql.{Row, SparkSession} imp ...
- ElasticSearch最全分词器比较及使用方法
介绍:ElasticSearch 是一个基于 Lucene 的搜索服务器.它提供了一个分布式多用户能力的全文搜索引擎,基于 RESTful web 接口.Elasticsearch 是用 Java 开 ...
- Docker入门与简单使用
前言: Docker 是一个开源的应用容器引擎,让开发者可以打包他们的应用以及依赖包到一个可移植的镜像中,然后发布到任何流行的Linux或Windows机器上.近几年来,Docker 在国内发展的如 ...
- 1021--RemoveOutermostParentheses
public class RemoveOutermostParentheses { /* 解法一:栈,( 进栈,) 出栈,栈为空时,则找到原语,然后去括号. */ public String remo ...
- BeyondCompare4破解方法
因为工作需要,经常会用到BeyondCompare4这个软件,但是从官方下载的BeyondCompare4只有一个月的试用期,点击输入密钥又一直打开购买软件的页面,所以就一开始就用了最笨的方法,软件的 ...
- 第五篇:Python函数基础篇
本篇介绍什么是函数.函数的特性.函数的定义.函数的调用.以及函数的参数.以及关于全局变量和局部变量的使用等等. 一.什么是函数: 函数是最基本的一种代码抽象方式,为了实现某种特定的功能而组织的带名字的 ...