哲学家进餐问题:使用信号量解决死锁
#include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <sys/sem.h> #include <sys/wait.h> #define N 5 // 哲学家的数量
// 定义信号量操作的结构体 struct sembuf P = {0, -1, SEM_UNDO}; struct sembuf V = {0, 1, SEM_UNDO};
// 定义信号量的标识符 int semid;
// 初始化信号量 void init_semaphore() { semid = semget(IPC_PRIVATE, 1, 0666 | IPC_CREAT); semctl(semid, 0, SETVAL, 1); }
// P操作 void sem_P() { semop(semid, &P, 1); }
// V操作 void sem_V() { semop(semid, &V, 1); }
// 哲学家进餐函数 void dining(int philosopher) { int left = philosopher; int right = (philosopher + 1) % N;
// 模拟进餐过程
printf('哲学家 %d 正在思考...
', philosopher); sleep(rand() % 3 + 1);
// 申请左手筷子
sem_P();
printf('哲学家 %d 拿到左手筷子...
', philosopher);
// 申请右手筷子
sem_P();
printf('哲学家 %d 拿到右手筷子...
', philosopher);
// 进餐
printf('哲学家 %d 正在进餐...
', philosopher); sleep(rand() % 3 + 1);
// 放下左手筷子
sem_V();
printf('哲学家 %d 放下左手筷子...
', philosopher);
// 放下右手筷子
sem_V();
printf('哲学家 %d 放下右手筷子...
', philosopher); }
int main() { // 初始化信号量 init_semaphore();
// 创建5个子进程表示5位哲学家
for (int i = 0; i < N; i++) {
pid_t pid = fork();
if (pid < 0) {
printf('进程创建失败
'); exit(1); } else if (pid == 0) { // 子进程调用哲学家进餐函数 dining(i); exit(0); } }
// 等待子进程结束
for (int i = 0; i < N; i++) {
wait(NULL);
}
// 删除信号量
semctl(semid, 0, IPC_RMID);
return 0;
}
原文地址: https://www.cveoy.top/t/topic/o5Cx 著作权归作者所有。请勿转载和采集!