生产者消费者问题
关系<br>
缓冲区空时,生产者必须先放入,消费者才能消耗:同步关系
缓冲区满时,消费者必须先取走,生产者才能放入:同步关系<br>
生产者和消费者访问缓冲区:互斥关系
实现<br>
semaphore mutex=1; //即产品池的访问权<br>semaphore empty=0; //即空缓冲区的数量<br>semaphore full=0; //即产品的数量<br>
Producer()
while(1) {<br> Produce();<br> P(empty);<br> P(mutex);<br> PutInto();<br> V(mutex);<br> V(full);<br>}<br>
Consumer()<br>
while(1) {<br> P(full);<br> P(mutex);<br> Get();<br> V(mutex);<br> V(full);<br> Consume();<br>}<br>
多生产者-多消费者问题
关系
缓冲区空时,生产者必须先放入,消费者才能消耗:同步关系
缓冲区满A时,消费者A必须先取走,生产者才能放入:同步关系
缓冲区满B时,消费者B必须先取走,生产者才能放入:同步关系
生产者AB、消费者AB对缓冲区的访问:互斥关系
实现
semaphore mutex=1;<br>semaphore A=0;<br>semaphore B=0;<br>semaphore empty=1;<br>
可以分析得:任何时刻A、B、empty最多只有1个为1,<br>即<font color="#F44336">最多只有一个进程不被阻塞</font>,因此可以去掉mutex<br>
如果缓冲区大小大于1,此时上述情况不总成立,mutex不可去
Class ProducerA<br>
while (1) {<br> ProduceA();<br> P(empty);<br> P(mutex);<br> PutInto();<br> V(mutex);<br> V(A);<br>}<br>
Class ProducerB
while (1) {<br> ProduceB();<br> P(empty);<br> P(mutex);<br> PutInto();<br> V(mutex);<br> V(B);<br>}<br>
Class ConsumerA
while (1) {<br> P(A);<br> P(mutex);<br> Get();<br> V(mutex);<br> V(empty);<br> Consume();<br>}<br>
Class ConsumerB
while (1) {<br> P(B);<br> P(mutex);<br> Get();<br> V(mutex);<br> V(empty);<br> Consume();<br>}<br>
吸烟者问题<br>单万能生产者-多消费者问题<br>
关系
缓冲区内有A时,消费者A才会取走A:同步关系
缓冲区内有B时,消费者B才会取走B:同步关系
缓冲区内有C时,消费者C才会取走C:同步关系
消费者完成消费时,生产者才为下一个消费者提供资源:同步关系
轮流关系是盲的,无需区分是谁完成了<br>
生产者和消费者ABC访问缓冲区:互斥关系
缓冲区大小为1,可去<br>
实现
semaphore mutex=1;<br>semaphore A=0;<br>semaphore B=0;<br>semaphore C=0;<br>semaphore finish=0;<br>
Class <font color="#F44336">MultiProducer</font><br>
while(1) {<br> ProduceA();<br> PutInto();<br> P(finish);<br> <br> ProduceB();<br> PutInto();<br> P(finish);<br><br> ProduceC();<br> PutInto();<br> P(finish);<br>}<br>
也可以用变量和循环控制
根据题目要求,最好用变量
Class ConsumerA<br>
while(1) {<br> P(A);<br> Get();<br> Consume();<br> V(finish);<br>}<br>
Class ConsumerB<br>
while(1) {<br> P(B);<br> Get();<br> Consume();<br> V(finish);<br>}<br>
Class ConsumerC<br>
while(1) {<br> P(C);<br> Get();<br> Consume();<br> V(finish);<br>}<br>
读者写者问题
关系
写者修改文件:互斥关系<br>
写者写时不允许读者读:互斥关系
<font color="#F44336">写者欲写时,阻止后来的读者进入读状态:互斥关系</font>
核心<br>
<font color="#F44336">利用count取消互斥</font><font color="#4CAF50"></font>
<font color="#4CAF50">用额外的信号量保证count互斥</font>
用PV包裹“读写非互斥量的代码段”可使其具备互斥性
<font color="#2196F3">用w保证写者不饥饿<br></font>
任何针对互斥量m的一组PV操作实际上阻断了<br>其他进程进入其被针对m的PV操作包裹的代码段<br>
亦可认为:<br>本进程一组对m的PV包裹的代码段执行<br>优先于其他进程被对m的PV包裹的代码段<br>
当进程A用P(m)V(m)包裹P(n)V(n),<br>而进程B用P(m)V(m)仅包裹P(n)时,<br>表明进程A执行P(n)V(n)所包裹的代码段<br>优先于进程B执行P(n)V(n)所包裹的代码段<br>
所谓优先,是当B类进程间不存在互斥关系,<br>而A类B类间存在互斥关系时,A类可以阻断<br>后来的B类进程资源请求,从而“强行插队”。<br>
实现
semaphore rw = 1;<br><font color="#F44336">int count = 0;<br><font color="#4CAF50">semaphore countMutex = 1;</font><br><font color="#2196F3">semaphore w = 1;</font></font><br>
Class Writer<br>
while(1) {<br> <font color="#2196F3">P(w);</font><br> P(rw);<br> Write();<br> V(rw);<br> <font color="#2196F3">V(w);</font><br>}<br>
Class Reader<br>
while(1) {<br> <font color="#2196F3">P(W);</font><br> <font color="#4CAF50">P(countMutex);</font><br> <font color="#F44336">if (count == 0)<br> <font color="#212121">P(rw);</font><br> count++;<br> <font color="#4CAF50">V(countMutex);</font><br></font> <font color="#2196F3">V(w);</font><br> Read();<br> <font color="#F44336"><font color="#4CAF50">P(countMutex);</font><br> count--;<br> if(count == 0)<br> <font color="#212121">V(rw);</font><br> <font color="#4CAF50">V(countMutex);</font></font><br>}<br>
哲学家进餐问题
关系
当进程拿到两个资源时,进程开始工作
进程工作结束后,释放占用的资源
进程获取资源是逐个的
进程获取不到需要的资源时,进程进入等待,不释放已经获得的资源
实现1<br>最多4人同时拿筷子<br>(总有一人可以吃饭)<br>
semaphore maxEater = 4;<br>semaphore chopstick[5] = [1, 1, 1, 1, 1 ];<br>
Class Philosopher<br>
while (1) {<br> P(maxEater);<br> P(chopstick[this]);<br> P(chopstick[(this + 1) % 5]);<br> Eat();<br> V(chopstick[this]);<br> V(chopstick[(this + 1) % 5]);<br> V(maxEater);<br> Think();<br>}<br>
实现2<br>奇偶位哲学家拿筷子策略不同<br>总有人一根筷子都拿不到<br>
semaphore chopstick[5] = [1, 1, 1, 1, 1 ];<br>
Class Philosopher<br>
while (1) {<br> if(this % 2 == 0) {<br> P(chopstick[this]);<br> P(chopstick[(this + 1) % 5]);<br> }<br> else {<br> P(chopstick[(this + 1) % 5]);<br> P(chopstick[this]);<br> }<br> Eat();<br> V(chopstick[this]);<br> V(chopstick[(this + 1) % 5]);<br> Think();<br>}<br>
实现3<br>只允许一人拿筷子<br>不能全拿别人都别想拿<br>
semaphore mutex = 1;<br>semaphore chopstick[5] = [1, 1, 1, 1, 1 ];<br>
Class Philosopher<br>
while (1) {<br> P(mutex);<br> P(chopstick[this]);<br> P(chopstick[(this + 1) % 5]);<br> V(mutex);<br> Eat();<br> V(chopstick[this]);<br> V(chopstick[(this + 1) % 5]);<br> Think();<br>}<br>