OS------经典进程的同步问题

1.生产者和消费者问题

这个问题一共有三个角色:生产者,消费者和缓冲池

对于这个问题,咱们分三个阶段来看

第一个问题,一个生产者,一个消费者和一个缓冲池怎么解决?

在解决问题之前先分析清楚需要干什么

  1. 进程
  2. 活动
  3. 分析关系
  4. 信号量

这是解决这类问题比较重要的四步

而关系又分为互斥,同步,资源

进程是两个,一个是生产者,一个是消费者

活动:生产和消费

关系:同步

接下来我们来写程序(伪代码):

写单词:buffer是缓冲的意思

semaphore empty=1,full=0;
producer(){
	while(1){
	    produce an item nextp;//生产出产品
	    wait(empty);
	    buffer=nextp;//将产品存入缓冲区
	    signal(full);
	}
}

consumer(){
	while(1){
		wait(full);
		nextc=buffer;
		signal(empty);
	}
}//将产品从缓冲区里取出,并置为空

bingo!第一个问题解决了

咱们来进阶一下

现在有一个生产者,一个消费者和n个缓冲区,该如何解决呢?
只需要在原来的基础上进行修改

既然有n个缓冲区,那咱们就设一个大小为n的数组好了

还需要加什么呢?对,需要进行取余运算

semaphore empty=1,full=0;
int in=0,out=0;
int buffer[n];
producer(){
	while(1){
	    produce an item nextp;
	    wait(empty);
	    buffer[in]=nextp;
	    in=(in+1)%n;
	    signal(full);
	}
}

consumer(){
	while(1){
		wait(full);
		nextc=buffer[out];
		out=(out+1)%n;
		signal(empty);
		consume the item in nextc;
	}
}

最后,我们来看有n个消费者,n个生产者,n个缓冲区的问题

semaphore empty=1,full=0,mutex=1;
int in=0,out=0;
int buffer[n];
producer(){
	while(1){
	    produce an item nextp;
	    wait(empty);
	    wait(mutex);
	    buffer[in]=nextp;
	    in=(in+1)%n;
	    signal(full);
	    signal(mutex);
	}
}

consumer(){
	while(1){
		wait(full);
		wait(mutex);
		nextc=buffer[out];
		out=(out+1)%n;
		signal(empty);
		signal(mutex);
		consume the item in nextc;
	}
}

看完了读者-写者问题咱们再看一个补充的题目

有一座东西方向的独木桥;用P,V操作实现:

1) 每次只允许一个人过桥;

2) 当独木桥上有自东向西的行人时,同方向的行人可以同时过桥,从西向东的方向,只允许一个人单独过桥。

(3) 当独木桥上有行人时,同方向的行人可以同时过桥,相反方向的人必须等待。

这个问题就可以简化为读者写者问题

第一种情况只允许一个人过桥,可以看成进程之间是互斥的。就跟读者跟写者之间是互斥的一样,只不过是没有这个身份上的差异罢了。

上伪代码:

semaphore s=1;
man(){
	while(1){
	    wait(s);
		过桥;
	    signal(s);	
	}
}//就设一个信号量让他们互斥使用就行了

 我们来看第二个问题:

这个就跟读者写者问题比较相似了,它分为从东向西和从西向东两个身份。

EastToWest(){
	wait(S1);
	if(EWcount==0){
		wait(S2);//申请互斥使用权 
	}
	EWcount++;
	signal(S1);
	过桥;
	wait(S1);
	EWcount--;
	if(EWcount==0){
		signal(S2);
	} 
	signal(S1);
}

WestToEast(){
	wait(S2);
	过桥;
	signal(S2); 
}

 

 

跟读者写者问题大差不差。

来看第三个进阶点的问题,就相当于是可以有多个读者同时去读,多个写者同时去写,但是读者和写者之间是互斥的关系。

需要修改的是进程WestToEast(); 

EastToWest(){
	wait(S1);
	if(EWcount==0){
		wait(S2);//申请互斥使用权 
	}
	EWcount++;
	signal(S1);
	过桥;
	wait(S1);
	EWcount--;
	if(EWcount==0){
		signal(S2);
	} 
	signal(S1);
}

WestToEast(){
	wait(S2);
	if(WEcount==0){
		wait(S1);//申请互斥使用权 
	}
	WEcount++;
	signal(S2);
	过桥;
	wait(S2);
	EWcount--;
	if(EWcount==0){
		signal(S1);
	} 
	signal(S2);
}

印象中和老师写的有点不太一样,她好像还设了一个S3,忘了怎么弄的了。。。

信号量的应用

习题一

在一个盒子里,混装了数量相等的黑白围棋子。

现在用自动分拣系统把黑子、白子分开,设分拣系统有两个进程P1P2

其中P1拣白子,P2拣黑子。规定当一个进程拣了一子后,必须让另一个进程去拣。

用信号量和PV操作协调两进程的活动。

Struct semaphore S1, S2;
S1.value=1; S2.value=0;
cobegin
   process P1(){              
   while(true){                          
   P(S1);                                   
   拣白子                                                      
   V(S1);
   }
}
coend
process P2(){
   while(true){
   P(S2);
   拣黑子
   V(S2);
   }
} 

习题二

   某控制系统中,数据采集进程负责把采集到的数据放到一缓冲区中,分析进程负责把数据从缓冲区中取出进行分析,试用信号量实现两者之间的同步

int Se=1;
int Sf=0;
mian(){
	cobegin;
	get();
	compute();
	coend 
} 
get(){
	while(采集工作未完成){
		采集一个数据;
		P(Se);
		将数据送入缓冲区;
		V(Sf); 
	} 
}
compute(){
	while(计算工作未完成){
		P(Sf);
		从缓冲区中取出数据;
		V(Se); 
		进行数据计算; 
	}
}

 

习题四 

一家四人父、母、儿子、女儿围桌而坐;桌上有一个水果盘; 

当水果盘空时,父亲可以放香蕉或者母亲可以放苹果,但盘中已有水果时,就不能放,父母等待。

当盘中有香蕉时,女儿可吃香蕉,否则,女儿等待;

当盘中有苹果时,儿子可吃,否则,儿子等待。

int S=1;
int So=0;
int Sa=0;
main(){
	cobegin;
	father();
	son();
	daughter();
	coend;
}

father(){
	while(1){
		P(S);
		将水果放入盘中;
		if(放入的是橘子){
			V(So);
		}else{
			V(Sa);
		}
	}
}

son(){
	while(1){
		P(So);
		从盘中取出橘子;
		V(S);
		吃橘子;
	}
}

daughter(){
	while(1){
		P(S);
		从盘中取出苹果;
		V(S); 
		吃苹果; 
	}
}

习题五

在公共汽车上,司机和售票员的活动分别是:

司机的活动:  启动车辆

        正常运行

        到站停车

售票员的活动: 关车门

        售票

        开车门

在汽车不断的到站,停车,行驶过程中,司机和售票员

的活动有什么同步关系?用信号量和P,V操作实现.

习题六

   有一个超市,最多可容纳N个人进入购物,当N个顾客满员时,后到的顾客在超市外等待;

超市中只有一个收银员。

可以把顾客和收银员看作两类进程,两类进程间存在同步关系。

写出用P;V操作实现的两类进程的算法

 

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值