62,614
社区成员
发帖
与我相关
我的任务
分享
class Writer extends Thread{
private Resource resource;
private int id; //读者进程id
public Writer(Resource resource, int id){
this.id = id;
this.resource = resource;
}
public void run(){
try{
resource.decreWmutex();
if(resource.getWmutex() < 0){ //如果wmutex已被某writer或reader进程占据,等待
System.out.println("写进程" + this.id + "被阻塞!");
wait();
}else{
System.out.println("写进程" + this.id + "正在操作!");
Thread.sleep(300);//正在访问时间
}
}catch(Exception e){
e.printStackTrace();
}finally{
resource.increWmutex();
System.out.println("写进程" + this.id + "操作完毕!");
synchronized(this){
notifyAll();
} //notifyAll();
}
}
}
class Reader extends Thread{
private Resource resource;
private int id;
public Reader(Resource resource, int id){
this.resource = resource;
this.id = id;
}
public void run(){
try{
resource.decreRmutex();
if(resource.getRmutex() < 0){
System.out.println("读进程" + this.id + "被阻塞!未进入");
wait();
}else{
if(resource.getReadercount() == 0){//如果是0,判断有没有写进程在里面。
resource.decreWmutex();
if(resource.getWmutex() < 0){
System.out.println("读进程" + this.id + "被阻塞!");
wait();
}
}
resource.increReadercount(); //增加一个reader进程
resource.increRmutex();//释放rmutex;
System.out.println("读进程" + this.id + "进入!" + "当前进程数是" + resource.getReadercount());
Thread.sleep(100);//模仿正在访问时间
resource.decreRmutex();//重新访问rmutex
if(resource.getRmutex() < 0){
System.out.println("读进程" + this.id + "被阻塞!未出来");
wait();
}else{
resource.decreReadercount();
if(resource.getReadercount() == 0) //如果,没有reader进程在里面,唤醒writer进程
resource.increWmutex();
}
}
}catch(Exception e){
e.printStackTrace();
}finally{
resource.increRmutex();//释放rmutex
System.out.println("读进程" + this.id + "操作完毕!" + "当前进程数是" + resource.getReadercount());
//notifyAll();
synchronized(this){
notifyAll();
}
}
}
}
public class RWProblem {
public static void main(String args[]){
Resource resource = new Resource();
//定义2个写者进程
for(int i = 0; i < 2; i++){
Thread t = new Writer(resource, i);
t.start();
}
//定义5个读者进程
for(int i = 0; i < 5; i++){
Thread t = new Reader(resource, i);
t.start();
}
}
}
public class IllegalMonitorStateException extends RuntimeException
public class IllegalMonitorStateExceptionextends RuntimeException
抛出的异常表明某一线程已经试图等待对象的监视器,或者试图通知其他正在等待对象的监视器而本身没有指定监视器的线程。
//定义资源类
class Resource{
private int wmutex;
private int rmutex;
private int readercount;
public Resource(){
wmutex = 1; //初始值为1,该资源信号量对reader进程和writer进程而言
rmutex = 1; //初始值为1,该资源信号量对所有reader进程而言。
readercount = 0; //记录访问文件的reader进程数
}
public synchronized void increWmutex(){
this.wmutex++;
}
public synchronized void decreWmutex(){
this.wmutex--;
}
public synchronized void increRmutex(){
this.rmutex++;
}
public synchronized void decreRmutex(){
this.rmutex--;
}
public synchronized void increReadercount(){
this.readercount++;
}
public synchronized void decreReadercount(){
this.readercount--;
}
public int getWmutex(){
return this.wmutex;
}
public int getRmutex(){
return this.rmutex;
}
public int getReadercount(){
return this.readercount;
}
}