9.经典进程同步问题

it2022-05-05  133

生产者消费者问题

 

 


读者-写者问题

 

 


哲学家进餐问题


哲学家就餐问题讨论

为防止死锁发生可采取的措施

  最多允许4个哲学家同时坐在桌子周围  仅当一个哲学家左右两边的筷子都可用时,才允许他拿筷子  给所有哲学家编号,基数号的哲学家必须首先拿左边的筷子,偶数号的哲学          家则反之  为了避免死锁,把哲学家分为三种状态,思考,饥饿,进食,并且一次拿到两只          筷子, 否则不拿

每个哲学家拿起第一根筷子一定时间后,若拿不到第二根筷子,再放下第一根筷子


  linux下的消费生产商品代码:

1 #include <semaphore.h> 2 #include <unistd.h> 3 #include <sys/types.h> 4 #include <pthread.h> 5 6 #include <stdlib.h> 7 #include <stdio.h> 8 #include <errno.h> 9 #include <string.h> 10 11 #define ERR_EXIT(m) \ 12 do \ 13 { \ 14 perror(m); \ 15 exit(EXIT_FAILURE); \ 16 }while(0) 17 18 #define CONSUMERS_COUNT 2 //消费者人数 19 #define PRODUCERS_COUNT 2 //生产者人数 20 #define BUFFSIZE 5 21 22 int g_buffer[BUFFSIZE];//缓冲区数目 23 24 unsigned short in = 0; //放入产品的指针(生产到哪个缓冲区) 25 unsigned short out = 0;//取出缓冲区指针(在哪个缓冲区消费的) 26 unsigned short produce_id = 0; 27 unsigned short consume_id = 0; 28 29 sem_t g_sem_full; //缓冲区可以生产的产品数 = BUFFSIZE 30 sem_t g_sem_empty; //缓冲区可以消费的产品数 = 0 31 pthread_mutex_t g_mutex;//互斥信号量 32 33 pthread_t g_thread[CONSUMERS_COUNT + PRODUCERS_COUNT]; 34 35 void *consume(void *arg) 36 { 37 int i; 38 int num = (int)arg; 39 while(1) 40 { 41 sem_wait(&g_sem_empty);//wait()操作 42 pthread_mutex_lock(&g_mutex);//互斥锁 43 44 //遍历缓冲区,看看有哪些缓冲区是可以生产消费的 45 for(i=0;i<BUFFSIZE;i++) 46 { 47 printf("%d 缓存区",i); 48 if(g_buffer[i] == -1) 49 printf("%s","为空"); 50 else 51 printf("%d",g_buffer[i]); 52 53 if(i==out) 54 printf("\t------消费"); 55 56 printf("\n"); 57 } 58 59 //produce()操作(生产产品) 60 consume_id = g_buffer[out]; 61 printf("%d 开始生产 产品 %d\n",num,consume_id); 62 g_buffer[out] = -1; 63 //将取出缓存区的指针偏移1(下个生产的位置) 64 out = (out+1) % BUFFSIZE; 65 printf("%d 生产商品 %d 结束",num,consume_id); 66 pthread_mutex_unlock(&g_mutex); 67 sem_post(&g_sem_full);//signal()操作 68 sleep(1); 69 } 70 return NULL; 71 72 } 73 74 void *produce(void *arg) 75 { 76 int num = (int)arg; 77 int i; 78 while(1) 79 { 80 sem_wait(&g_sem_full); 81 pthread_mutex_lock(&g_mutex); 82 83 //遍历缓冲区,看看有哪些缓冲区是可以生产产品的 84 for(i=0;i<BUFFSIZE;i++) 85 { 86 printf("%d 缓存区",i); 87 if(g_buffer[i] == -1) 88 { 89 90 printf("%s","为空"); 91 } 92 else 93 printf("%d",g_buffer[i]); 94 95 if(i==in) 96 printf("\t------生产"); 97 98 printf("\n"); 99 } 100 101 printf("%d 开始生产产品 %d\n",num,produce_id); 102 g_buffer[in] = produce_id; 103 in = (in+1)%BUFFSIZE; 104 printf("%d 产品结束生产 %d\n",num,produce_id++); 105 pthread_mutex_unlock(&g_mutex); 106 sem_post(&g_sem_empty); 107 sleep(5); 108 } 109 return NULL; 110 } 111 112 int main() 113 { 114 int i; 115 for(i=0;i<BUFFSIZE;i++) 116 g_buffer[i] = -1; 117 118 sem_init(&g_sem_full,0,BUFFSIZE); 119 sem_init(&g_sem_empty,0,0); 120 121 pthread_mutex_init(&g_mutex,NULL); 122 123 for(i=0;i<CONSUMERS_COUNT;i++) 124 pthread_create(&g_thread[i],NULL,consume,(void *)i); 125 126 for(i=0;i<CONSUMERS_COUNT;i++) 127 pthread_create(&g_thread[i],NULL,produce,(void *)i); 128 129 for(i=0;i<CONSUMERS_COUNT;i++) 130 pthread_join(g_thread[i],NULL); 131 132 sem_destroy(&g_sem_full); 133 sem_destroy(&g_sem_empty); 134 sem_destroy(&g_mutex); 135 136 return 0; 137 138 } View Code

 linux下哲学家进餐代码

1 #include <pthread.h> 2 #include <stdio.h> 3 #include <stdlib.h> 4 5 6 #define N 5 7 #define LEFT (i+N-1)%N 8 #define RIGHT (i+1)%N 9 #define THINK_TIME 3 10 #define EAT_TIME 2 11 12 enum { THINKING, HUNGRY, EATING } state[N]; 13 14 pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER, s[N]; 15 16 //如果能吃法就吃饭 17 void test(int i) 18 { 19 if (state[i] == HUNGRY 20 && state[LEFT] != EATING 21 && state[RIGHT] != EATING) 22 { 23 state[i] = EATING; 24 pthread_mutex_unlock(&s[i]);//哲学家饱了 25 } 26 } 27 28 //第i个哲学家饿了 29 void take_forks(int i) 30 { 31 pthread_mutex_lock(&mutex); 32 state[i] = HUNGRY; 33 test(i); 34 pthread_mutex_unlock(&mutex); 35 pthread_mutex_lock(&s[i]);//等待哲学家饿了 36 } 37 38 //第i个哲学家思考 39 void put_forks(int i) 40 { 41 pthread_mutex_lock(&mutex); 42 state[i] = THINKING; 43 test(LEFT); 44 test(RIGHT); 45 pthread_mutex_unlock(&mutex); 46 } 47 48 void think(int i) 49 { 50 printf("philosopher %d is thinking...\n", i); 51 sleep(THINK_TIME); 52 } 53 54 void eat(int i) 55 { 56 printf("philosopher %d is eating...\n", i); 57 sleep(EAT_TIME); 58 } 59 60 //线程函数 61 void* phi(void* vargp) 62 { 63 int i = *(int*)vargp; 64 while (1) 65 { 66 think(i); 67 take_forks(i); 68 eat(i); 69 put_forks(i); 70 } 71 return NULL; 72 } 73 74 int main() 75 { 76 int i; 77 pthread_t tid[N]; 78 for (i = 0; i < N; i++) 79 pthread_create(&tid[i], NULL, phi, (void*)(&i)); 80 for (i = 0; i < N; i++) 81 pthread_join(tid[i], NULL); 82 return 0; 83 } View Code

注意编译时候后面要加上 -lpthread

 

转载于:https://www.cnblogs.com/xiaochi/p/8029636.html


最新回复(0)