当前位置:主页 > 查看内容

操作系统实验—进程同步(吃水果问题)

发布时间:2021-05-29 00:00| 位朋友查看

简介:题目 桌上有一空盘最多允许存放一只水果。爸爸可向盘中放一个苹果或放一个桔子儿子专等吃盘中的桔子女儿专等吃苹果。 试用P、V操作实现爸爸、儿子、女儿三个并发进程的同步。 提示设置一个信号量表示可否向盘中放水果一个信号量表示可否取桔子一个信号量表示……

题目

桌上有一空盘,最多允许存放一只水果。爸爸可向盘中放一个苹果或放一个桔子,儿子专等吃盘中的桔子,女儿专等吃苹果。
试用P、V操作实现爸爸、儿子、女儿三个并发进程的同步。

提示:设置一个信号量表示可否向盘中放水果,一个信号量表示可否取桔子,一个信号量表示可否取苹果。

实验目的:

深入掌握进程、线程同步机制——信号量机制的原理与应用;
掌握Windows编程中信号量机制的使用方法;
掌握Windows下线程的控制方法;
可进行简单的信号量应用编程。

解题思路

下面展示一些 内联代码片

从这个题意可以得出,这个实验一共有3个进程,
分别是父亲,儿子,女儿。
且要设置3个信号量,
S:表示是否可以向盘子防水果  初值为1 表示盘子为空
S0:表示盘子中放的是桔子 初值为0  表示盘子内不是桔子
S1:表示盘子中放的是苹果 初值为0 表示盘子内不是苹果
// 进行P,V操作(P,V操作为原子操作不可被打断)
//父亲
father()
{ while(1){
  P(S);//申请盘子的使用权
  将水果放入盘中
  if(是桔子){
  V(S0);//释放是桔子的信号量,S0+1)
  }
  else{
  V(S1);//释放是苹果的信号量,S1+1)
  }
}
}

//儿子
son() 
{while(1){
  p(S0);//等待盘子中是桔子的信号
  取桔子;
  V(S);释放盘子的使用权
  吃桔子;
}
}

//女儿
daughter() 
{while(1){
  p(S1);//等待盘子中是苹果的信号
  取苹果;
  V(S);释放盘子的使用权
  吃苹果;
}
}

源码实现

#include <windows.h>
#include <iostream>
#include<stdio.h>

bool g_continue = true; //控制程序结束
HANDLE g_hS; //当盘子为空时的线程 
HANDLE g_hS0; //当盘子中放的是桔子线程 
HANDLE g_hS1; //当盘子中放的是苹果线程 
DWORD WINAPI father(LPVOID); //定义父亲线程
DWORD WINAPI son(LPVOID); //定义儿子线程
DWORD WINAPI daughter(LPVOID);//定义女儿线程
int main()  
{  
 //创建各个互斥与资源信号量  
 g_hS = CreateSemaphore(NULL,1,1,NULL);  //盘子中是否有水果 
 g_hS0 = CreateSemaphore(NULL,0,1,NULL);  //盘子中的水果为桔子 
 g_hS1 = CreateSemaphore(NULL,0,1,NULL);  //盘子中的水果为苹果 

//其中第2和3个参数为信号量的初始值和最大值

 const unsigned short father_COUNT = 0; //声明父亲
 const unsigned short son_COUNT = 0; //声明儿子
 const unsigned short daughter_COUNT = 0;//声明女儿
 
 //总的线程数 
 const unsigned short THREADS_COUNT = father_COUNT+son_COUNT+daughter_COUNT ;  
 HANDLE hThreads[THREADS_COUNT]; //各线程的handle  
 DWORD fatherID[father_COUNT]; //父亲线程的标识符
 DWORD sonID[son_COUNT]; //儿子线程的标识符  
 DWORD daughterID[daughter_COUNT]; //女儿线程的标识符
 
//创建父亲进程

 hThreads[0]=CreateThread(NULL,0,father,NULL,0,&fatherID[0]);  
  if (hThreads[0]==NULL) return -1;  
 
//创建儿子进程
  
 hThreads[1]=CreateThread(NULL,0,son,NULL,0,&sonID[0]);  
  if (hThreads[1]==NULL) return -1;  
 
//创建女儿进程
 
 hThreads[2]=CreateThread(NULL,0,daughter,NULL,0,&daughterID[0]);  
  if (hThreads[2]==NULL) return -1;  


 while(g_continue){  
  if(getchar()){ //按回车后终止程序运行  
	  g_continue = false;  
  }  
 }  

 return 0;  
}  
//父亲放水果的操作,输出  

void eat()  
{  
 std::cerr << "儿子吃桔子" << std::endl;  
}  

 
void eat1()  
{  
 std::cerr << "女儿吃苹果" << std::endl;  
}  

//父亲进程  
DWORD WINAPI father(LPVOID lpPara)  
{  
 while(g_continue){  
  WaitForSingleObject(g_hS,INFINITE);   
  
  int juzhi=rand()%2; //设置了一个随机数,来模拟父亲放的是什么水果 
  Sleep(1500);//方便观察实验结果
  if(juzhi==1){
  	  printf("父亲放入了一个桔子\n");
  	  Sleep(1000);
      ReleaseSemaphore(g_hS0,1,NULL); 
  }
  else{
  	printf("父亲放入了一个苹果\n"); 
  	Sleep(1000);
	   ReleaseSemaphore(g_hS1,1,NULL); 
 }
 }  
 return 0;  
}  

//儿子进程 
DWORD WINAPI son(LPVOID lpPara)  
{  
 while(g_continue){  
  WaitForSingleObject(g_hS0,INFINITE); 
   eat(); 
   Sleep(1500); 
  ReleaseSemaphore(g_hS,1,NULL);   
 }  
 return 0;  
}    

//女儿进程 
DWORD WINAPI daughter(LPVOID lpPara)  
{  
 while(g_continue){  
  WaitForSingleObject(g_hS1,INFINITE);    
  eat1(); 
  Sleep(1500); 
  ReleaseSemaphore(g_hS,1,NULL); 
 }  
 return 0;  
}    

实验结果

在这里插入图片描述
Thanks

;原文链接:https://blog.csdn.net/m0_56145255/article/details/115551222
本站部分内容转载于网络,版权归原作者所有,转载之目的在于传播更多优秀技术内容,如有侵权请联系QQ/微信:153890879删除,谢谢!
上一篇:Signal Tap抓取波形 下一篇:没有了

推荐图文


随机推荐