在PV操作中会有一个经典的例子就是爸爸妈妈儿子女儿吃水果问题,爸爸妈妈向盘子里放入水果,儿子女儿向盘子取水果。然而爸爸只向盘子放苹果,妈妈只向盘子放橘子,女儿只能吃苹果,儿子只能吃橘子。并且盘子里只能

在PV操作中会有一个经典的例子就是爸爸妈妈儿子女儿吃水果问题,爸爸妈妈向盘子里放入水果,儿子女儿向盘子取水果。然而爸爸只向盘子放苹果,妈妈只向盘子放橘子,女儿只能吃苹果,儿子只能吃橘子。并且盘子里只能装一个水果,这样爸爸妈妈就要竞争盘子向里面放入水果。而儿子女儿取走水果后必须通知爸爸妈妈向里面放入水果。这就是一个典型的PV操作中互斥与同步混合模型。代码如下:

View Code 
 class Program
     {
         private static Semaphore apple = new Semaphore(0, 1);
         private static Semaphore pear = new Semaphore(0, 1);
         private static Semaphore s=new Semaphore(1,1);
         static void Main(string[] args)
         {
             Thread father = new Thread(new ThreadStart(Father));
             Thread mather = new Thread(new ThreadStart(Mather));
             Thread son = new Thread(new ThreadStart(Son));
             Thread daugther = new Thread(new ThreadStart(Daugther));
             father.Name = "爸爸";
             mather.Name = "妈妈";
             son.Name = "儿子";
             daugther.Name = "女儿";
             father.Start();
             mather.Start();
             son.Start();
             daugther.Start();
         }
         private static void Father()
         {
             Console.WriteLine("{0}准备就绪",Thread.CurrentThread.Name);
             s.WaitOne();
             Console.WriteLine("{0}放入一个苹果", Thread.CurrentThread.Name);
             Thread.Sleep(1000);
             apple.Release();
         }
         private static void Mather()
         {
             Console.WriteLine("{0}准备就绪", Thread.CurrentThread.Name);
             s.WaitOne();
             Console.WriteLine("{0}放入一个梨子", Thread.CurrentThread.Name);
             Thread.Sleep(1000);
             pear.Release();
         }
         private static void Son()
         {
             Console.WriteLine("{0}准备就绪", Thread.CurrentThread.Name);
             Thread.Sleep(1000);
             pear.WaitOne();
             Console.WriteLine("{0}取出一个梨子", Thread.CurrentThread.Name);
             s.Release();
         }
         private static void Daugther()
         {
             Console.WriteLine("{0}准备就绪", Thread.CurrentThread.Name);
             Thread.Sleep(1000);
             apple.WaitOne();
             Console.WriteLine("{0}取出一个苹果", Thread.CurrentThread.Name);
             s.Release();
         }
     }

运行结果如下:

(由Dijkstra首先提出并解决)5个哲学家围绕一张圆桌而坐,桌子上放着5支筷子,每两个哲学家之间放一支;哲学家的动作包括思考和进餐,进餐时需要同时拿起他左边和
右边的两支筷子,思考时则同时将两支筷子放回原处。试想一下,如果哲学家同时思考完问题一人拿一支筷子,每人都等待左边或者右边的人吃完放下筷子,者无人能进餐,只有饿死。那么就必须对此进行PV控制。还有一种情况就是形成死锁,每个哲学家从左边开始取筷子,结果每人一人拿一支筷子互相等待,形成死锁。见下图

View Code 
 class Program
     {
         private static Semaphore s1 = new Semaphore(1, 1);
         private static Semaphore s2 = new Semaphore(1, 1);
         private static Semaphore s3 = new Semaphore(1, 1);
         private static Semaphore s4 = new Semaphore(1, 1);
         private static Semaphore s5 = new Semaphore(1, 1);
         static void Main(string[] args)
         {
                 Thread thread1 = new Thread(new ThreadStart(L1));
                 Thread thread2 = new Thread(new ThreadStart(L2));
                 Thread thread3 = new Thread(new ThreadStart(L3));
                 Thread thread4 = new Thread(new ThreadStart(L4));
                 Thread thread5 = new Thread(new ThreadStart(L5));
                 thread1.Start();
                 thread2.Start();
                 thread3.Start();
                 thread4.Start();
                 thread5.Start();
         }
         private static void L1()
         {
             Console.WriteLine("哲学家1思考结束");
             s1.WaitOne();
             Console.WriteLine("哲学家1可以取左边的筷子");
             s2.WaitOne();
             Console.WriteLine("哲学家1可以取右边的筷子,并且可以吃饭了");
             Console.WriteLine("哲学家1吃饭结束,放下筷子");
             Thread.Sleep(1000);
             s1.Release();
             s2.Release();
         }
         private static void L2()
         {
             Console.WriteLine("哲学家2思考结束");
             s2.WaitOne();
             Console.WriteLine("哲学家2可以取左边的筷子");
             s3.WaitOne();
             Console.WriteLine("哲学家2可以取右边的筷子,并且可以吃饭了");
             Console.WriteLine("哲学家2吃饭结束,放下筷子");
             Thread.Sleep(1000);
             s2.Release();
             s3.Release();
         }
         private static void L3()
         {
             Console.WriteLine("哲学家3思考结束");
             s3.WaitOne();
             Console.WriteLine("哲学家3可以取左边的筷子");
             s4.WaitOne();
             Console.WriteLine("哲学家3可以取右边的筷子,并且可以吃饭了");
             Console.WriteLine("哲学家3吃饭结束,放下筷子");
             Thread.Sleep(1000);
             s3.Release();
             s4.Release();
         }
         private static void L4()
         {
             Console.WriteLine("哲学家4思考结束");
             s4.WaitOne();
             Console.WriteLine("哲学家4可以取左边的筷子");
             s5.WaitOne();
             Console.WriteLine("哲学家4可以取右边的筷子,并且可以吃饭了");
             Console.WriteLine("哲学家4吃饭结束,放下筷子");
             Thread.Sleep(1000);
             s4.Release();
             s5.Release();
         }
         private static void L5()
         {
             Console.WriteLine("哲学家5思考结束");
             s1.WaitOne();
             Console.WriteLine("哲学家5可以取左边的筷子");
             s5.WaitOne();
             Console.WriteLine("哲学家5可以取右边的筷子,并且可以吃饭了");
             Console.WriteLine("哲学家5吃饭结束,放下筷子");
             Thread.Sleep(1000);
             s1.Release();
             s5.Release();
         }
     }


运行结果如下:

 


 

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值