java 与操作系统同步问题(三)————父亲儿子女儿水果问题
问题描述:父亲每次都会放一个水果在桌子上,女儿喜欢吃香蕉(只吃香蕉), 儿子喜欢吃苹果(只吃苹果)。父亲每次只会随机往桌子上放一个水果(苹果或香蕉),儿子,女儿会来取。使用p、v操作来完成父亲、儿子、女儿的同步行为模拟。
问题分析:由上述描述我们可以知道,桌子就是一个缓冲区(单缓冲),同一时刻,只能有一个人对它进行放和取得操作。所以桌子就是一个互斥信号量。而桌子上有苹果,且父亲没有放,儿子才能取,女儿也是同理。所以应该还有两个资源信号量:1 苹果 2 香蕉
在由题意分析可知,三个信号量的初始值应该为 1 0 0 因为桌子只能放一个水果。而在开始的时候,桌子上是空的(所以可以进行放的操作),所以苹果、香蕉初始资源量都为空。
代码实现:
1.信号量设定如下:
/**
* 缓冲区是否满信号量
*/
Semaphore empty; /**
* 苹果信号量
*/
Semaphore apple; /**
* 香蕉信号量
*/
Semaphore banana; empty = new Semaphore(1);
apple = new Semaphore(0);
banana = new Semaphore(0);
2.父亲的放的线程,只有在桌子互斥资源量可以用的时候才能进行放的操作。所以要先p一下桌子信号量。
Thread fatherThread = new Thread(new Runnable() {
String className = "father";
@Override
public void run() {
// TODO Auto-generated method stub
while(true) {
Semaphore.Wait(empty, className);
if (randomAB()) {
System.out.println(className + "往盘子里放了一个苹果");
Semaphore.Signal(apple, className);
} else {
System.out.println(className + "往盘子里放了一个香蕉");
Semaphore.Signal(banana, className);
}
System.out.println(className + "完成了一次放的操作");
//随机生成休眠时间,代表放入产品的操作时间
long millis = (long) (Math.random() * 1000);
try {
Thread.sleep(millis);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
});
3.儿子的实现,要判断是否有苹果,没有的话就等待
Thread sonThread = new Thread(new Runnable() {
String className = "son";
@Override
public void run() {
// TODO Auto-generated method stub
while(true) {
Semaphore.Wait(apple, className);
System.out.println(className + "从盘子里取了一个苹果");
//随机生成休眠时间,代表放入产品的操作时间
long millis = (long) (Math.random() * 1000);
try {
Thread.sleep(millis);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
System.out.println(className + "吃了一个苹果");
Semaphore.Signal(empty, className);
System.out.println(className + "完成了一次取吃的操作");
}
}
});
4.女儿的代码实现:原理跟儿子的类似
Thread daughterThread = new Thread(new Runnable() {
String className = "daughter";
@Override
public void run() {
// TODO Auto-generated method stub
while(true) {
Semaphore.Wait(banana, className);
System.out.println(className + "从盘子里取了一个香蕉");
//随机生成休眠时间,代表放入产品的操作时间
long millis = (long) (Math.random() * 1000);
try {
Thread.sleep(millis);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
System.out.println(className + "吃了一个香蕉");
Semaphore.Signal(empty, className);
System.out.println(className + "完成了一次取吃的操作");
}
}
});
运行结果如下:
daughter被阻塞
son被阻塞
father往盘子里放了一个香蕉
father资源量足够,唤醒一个
father完成了一次放的操作
daughter从盘子里取了一个香蕉
daughter吃了一个香蕉
daughter完成了一次取吃的操作
daughter被阻塞
father往盘子里放了一个香蕉
father资源量足够,唤醒一个
father完成了一次放的操作
daughter从盘子里取了一个香蕉
father被阻塞
daughter吃了一个香蕉
daughter资源量足够,唤醒一个
daughter完成了一次取吃的操作
....
java 与操作系统同步问题(三)————父亲儿子女儿水果问题的更多相关文章
- JAVA之线程同步的三种方法
最近接触到一个图片加载的项目,其中有声明到的线程池等资源需要在系统中线程共享,所以就去研究了一下线程同步的知识,总结了三种常用的线程同步的方法,特来与大家分享一下.这三种方法分别是:synchroni ...
- Java中实现线程同步的三种方法
实现同步的三种方法 多线程共享数据时,会发生线程不安全的情况,多线程共享数据必须同步. 实现同步的三种方法: 使用同步代码块 使用同步方法 使用互斥锁ReetrantLock(更灵活的代码控制) 代码 ...
- java面试基础题(三)
程序员面试之九阴真经 谈谈final, finally, finalize的区别: final:::修饰符(关键字)如果一个类被声明为final,意味着它不能再派生出新的子类,不能作为父类被继承.因此 ...
- Java IO:同步、非堵塞式IO(NIO)
转载请注明出处:jiq•钦's technical Blog 引言 JDK1.4中引入了NIO,即New IO,目的在于提高IO速度.特别注意JavaNIO不全然是非堵塞式IO(No-Blocking ...
- java两种同步机制的实现 synchronized和reentrantlock
java两种同步机制的实现 synchronized和reentrantlock 双11加保障过去一周,趁现在有空,写一点硬货,因为在进入阿里之后工作域的原因之前很多java知识点很少用,所以记录一下 ...
- Java中线程同步的理解
我们可以在计算机上运行各种计算机软件程序.每一个运行的程序可能包括多个独立运行的线程(Thread). 线程(Thread)是一份独立运行的程序,有自己专用的运行栈.线程有可能和其他线程共享一些资源, ...
- java中线程同步的理解(非常通俗易懂)
转载至:https://blog.csdn.net/u012179540/article/details/40685207 Java中线程同步的理解 我们可以在计算机上运行各种计算机软件程序.每一个运 ...
- Java 并发 线程同步
Java 并发 线程同步 @author ixenos 同步 1.异步线程本身包含了执行时需要的数据和方法,不需要外部提供的资源和方法,在执行时也不关心与其并发执行的其他线程的状态和行为 2.然而,大 ...
- JAVA面试之集合框架(三)
21.ArrayList和Vector的区别 这两个类都实现了List接口(List接口继承了Collection接口),他们都是有序集合,即存储在这两个集合中的元素的位置都是有顺序的,相当于一种动态 ...
随机推荐
- Python爬虫 Cookie的使用
Cookie,指某些网站为了辨别用户身份.进行session跟踪而储存在用户本地终端上的数据(通常经过加密) 比如说有些网站需要登录后才能访问某个页面,在登录之前,你想抓取某个页面内容是不允许的.那么 ...
- Webdriver API之操作(一)
一. 控制浏览器 1. 控制浏览器大小 driver.set_window_size(480,800) #浏览器宽480,高800显示 dirver.maximize_window() #浏览器最大化 ...
- 安装hadoop2.7.3
hadoop3与hadoop2.x的变化很大,hadoop3很多东西现在做起来太麻烦了,这里先安装hadoop2.7.3 此贴学习地址http://www.yiibai.com/t/mapreduce ...
- iOS·官方文档译文框架源码注解
导语
- 短路运算|字符串操作函数|内存mem操作函数
body, table{font-family: 微软雅黑; font-size: 10pt} table{border-collapse: collapse; border: solid gray; ...
- JVM 堆内存,参数优化
Java堆内存 http://www.importnew.com/19593.html JVM诊断之查看运行参数 JVM 垃圾回收器工作原理及使用实例介绍 https://www.ibm.com/de ...
- Gym - 101102C线段树
Judge Bahosain was bored at ACM AmrahCPC 2016 as the winner of the contest had the first rank from t ...
- OC 动态类型和静态类型
多态 允许不同的类定义相同的方法 动态类型 程序直到执行时才能确定所属的类 静态类型 将一个变量定义为特定类的对象时,使用的是静态形态 将一个变量定义为特定类的对象时,使用的是静态类型,在编译的时候就 ...
- Linux下memcache的安装和启动测试
memcache是一套分布式的高速缓存系统,MemCache的工作流程如下:先检查客户端的请求数据是否在memcached中,如有,直接把请求数据返回,不再对数据库进行任何操作:如果请求的数据不在me ...
- hammer的初始化及移动端各种滑动
前言:本人对hammer了解不是很多,早做项目时遇到了手机端的一些滑动事件,特此分析下hammer的某些属性. hammer.js是一款开源的移动端脚本框架,他可以完美的实现在移端开发的大多数事件,如 ...