/* signal(full); */ until false; end consumer: begin repeat wait(mutex);
wait(empty); /* 应为wait(full),而且还应该在wait(mutex)的前面 */ nextc:=buffer(out);
out:=out+1; /* 考虑循环,应改为: out:=(out+1) mod n; */ signal(mutex); /* signal(empty); */ consumer item in nextc; until false; end
10 试利用记录型信号量写出一个不会出现死锁的哲学家进餐问题的算法.
设初始值为1的信号量c[I]表示I号筷子被拿(I=1,2,3,4,...,2n),其中n为自然数. send(I):
Begin
if I mod 2==1 then { P(c[I]);
P(c[I-1 mod 5]); Eat;
V(c[I-1 mod 5]); V(c[I]); } else {
P(c[I-1 mod 5]); P(c[I]); Eat; V(c[I]);
V(c[I-1 mod 5]); } End
11 在测量控制系统中的数据采集任务,把所采集的数据送一单缓冲区;计算任务从该单缓冲中取出数据
进行计算.试写出利用信号量机制实现两者共享单缓
冲的同步算法. int mutex=1; int empty=n; int full=0; int in=0; int out=0; main() { cobegin send(); obtain(); coend } send() { while(1) { . .
collect data in nextp; . .
wait(empty); wait(mutex); buffer(in)=nextp; in=(in+1) mod n; signal(mutex); signal(full); } }//send obtain() { while(1) {
wait(full); wait(mutex); nextc:=buffer(out); out:=(out+1) mod n; signal(mutex); signal(empty);
culculate the data in nextc; }//while }//obtain
12 画图说明管程由哪几部分组成?为什么要引入条
件变量?管程由三部分组成:局部于管程的共享变量说明;对该数据结构进行操作的一组过程;对局部于管程的
数据设置初始值的语句. (图见P80)因为调用wait原语后,使进程等待的原因有多种,为了区别它们,引入了条件变量.
13 如何利用管程来解决生产者-消费者问题? (见P82)
14 什么是AND信号量?试利用AND信号量写出生产者-消费者问题的解法.
为解决并行所带来的死锁问题,在wait操作中引入AND条件,其基本思想是将进程在整个运行过程中所需要的所有临界资源,一次性地全部分配给进程,用完后一次性释放.
解决生产者-消费者问题可描述如下: var mutex,empty,full: semaphore:=1,n,0; buffer: array[0,...,n-1] of item; in,out: integer:=0,0; begin parbegin producer: begin repeat