【操作系统】哲学界进餐问题实现

编程入门 行业动态 更新时间:2024-10-07 11:30:31

【操作系统】<a href=https://www.elefans.com/category/jswz/34/1769917.html style=哲学界进餐问题实现"/>

【操作系统】哲学界进餐问题实现

目录

实验原理:

实验目的:

实验数据及结果分析:


  • 实验原理:

哲学家进餐问题可以通过限制同时进餐人数为4解决,为此需要设置一个值为4的互斥信号量sem_eaters,并且每根筷子只能同时由一个人使用,需要设置一个值为1的互斥信号量数组sem_chopstics。C语言中提供了实现信号量和线程创建等方法的库,可以使用C语言在ubuntu操作系统上实现哲学家进餐问题的解决。

  • 实验目的:

  1. 掌握哲学家就餐问题,掌握预防死锁的实现方法;
  2. 了解Linux系统下进程和线程的实现;
  3. 掌握通过互斥量、POSIX信号量、XSI信号量集实现多线程/多进程同步控制的方法
  • 实验内容:

熟悉Ubuntu系统环境和命令;熟悉Ubuntu系统下的多线程/多进程编程;在Ubuntu系统下编程实现哲学家就餐问题。实现教材2.5.2节中所描述的哲学家就餐问题。要求显示出每个哲学家的工作状态,如吃饭,思考。连续运行30次以上都未出现死锁现象。

  • 实验器材(设备、元器件):

PC计算机,操作系统:Ubuntu

  • 实验步骤:
  1. 了解C语言实现线程互斥中的信号量、线程等使用方式

本实验主要用到了POSIX信号量,来自semaphore.h和来自pthread.h的线程创建等方法。

如sem_init()初始化信号量,sem_post()对信号量进行V操作,phtread_create()创建线程等函数,实现哲学家进餐问题。

  1. 考虑哲学家进餐问题的实现

本次实验中采用约束同时进餐人数的方式避免死锁发生,当同时进餐人数最多为4人的时候,不会发生死锁(还有同时请求两根筷子等解决方案,这里只说明其中一种)。可以通过一个初始值为4的信号量sem_eaters控制,以达到目的。

  1. 编写代码

图1

  1. 使用gcc编译.c文件

图2

  1. 执行编译后的文件

图3

  1. 运行结果

图4

  • 实验数据及结果分析:

实验数据

类型

初始化

sem_eaters信号量

sem_t

sem_init 值为4

sem_chopstics信号量数组

sem_t

sem_init 值为1

PID数组

Int

{0,1,2,3,4}

pthreads数组

pthread_t

使用pthread_create初始化

循环次数

Int

70

通过70次循环哲学家问题,没有发现报错,即没有出现死锁,均正常执行。

实验代码如下:

  1.  #include <stdio.h>
  2.  #include <stdlib.h>
  3.  #include <pthread.h> 
  4.  #include <semaphore.h>
  5.  sem_t sem_eaters;//记录哲学家信号量
  6.  sem_t sem_chopstics[5];//记录筷子信号量
  7.  int PID[5] = {0,1,2,3,4};//记录进程ID
  8.  int num = 0;//记录当前已进餐人数
  9.  //初始化
  10.  void init(){
  11.   int i =  0, j ,k;
  12.   for (;i  < 5;i++)
  13.   {
  14.    j = sem_init(&sem_chopstics[i],0,1);//初始化每一根筷子为值为1的信号量
  15.    if (j == -1) {
  16.     perror("初始化sem_chopstics信号量失败\n");
  17.     exit(1);
  18.    }
  19.   }
  20.   k = sem_init(&sem_eaters,0,4);//初始化哲学家信号量,即控制同时进餐的人数
  21.   if (k == -1)
  22.   {
  23.    perror("初始化sem_eaters信号量失败\n");
  24.    exit(1);
  25.   }
  26.  }
  27.  void * method(int* pid){
  28.   int p_num = (*pid) % 5;//当前进餐的哲学家编号
  29.   pirntf("当前第%d号哲学家思考中\n",&p_num);
  30.   sem_wait(&sem_eaters);
  31.   printf("拿起第%d根筷子\n",&p_num);
  32.   sem_wait(&sem_chopstics[p_num]);
  33.   printf("拿起第%d根筷子\n",&((p_num+1) % 5));
  34.   sem_wait(&sem_chopstics[(p_num+1)%5]);
  35.   pirntf("当前第%d号哲学家正在进餐~~\n",&p_num);
  36.   num++;//吃完了
  37.   pirntf("当前第%d号哲学家已经吃完了\n",&p_num);
  38.   //释放资源
  39.   sem_post(&sem_chopstics[(p_num)%5]);
  40.   sem_post(&sem_chopstics[(p_num+1)%5]);
  41.   sem_post(&sem_eaters);
  42.  }
  43.  int main()
  44.  {
  45.   for (int i = 1;i <= 50 ;i++ )
  46.   {
  47.    pthread_t pthreads[5];
  48.    printf("这是第%d次哲学家进餐问题\n",&i);
  49.    init();//初始化信号量
  50.    for (int j = 0;j < 5 ;j++ )
  51.    {
  52.     printf("创建第%d号线程\n",j);
  53.     int k = 0;
  54.     k = pthread_create(&pthreads[j],NULL,method,&PID[j]);//传入进程执行的方法method 要求是void *类型,并且传入函数需要的参数
  55.     if  (k == -1) {
  56.      perror("线程创建失败\n");
  57.      exit(1);
  58.     }
  59.    }
  60.    for (int l = 0; l < 5;l++ )
  61.    {
  62.     pthread.join(pthreads[l],NULL);
  63.    }
  64.    //结束:销毁所有信号量
  65.    sem_destroy(&sem_eaters);
  66.    for (int p = 0;p < 5;p++) {
  67.     sem_destroy(&sem_chopstics[p]);
  68.    }
  69.    num = 0;
  70.   }
  71.   return 0;
  72.  }

更多推荐

【操作系统】哲学界进餐问题实现

本文发布于:2024-02-28 11:02:04,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1769229.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:哲学   操作系统

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!