📄 led.c
字号:
#include <stdio.h>
#include <unistd.h>
#include <limits.h>
#include <errno.h>
#include <string.h>
#include <stdlib.h>
#include <sys/stat.h>
#include <sys/ipc.h>
#include <sys/sem.h>#include <sys/shm.h>#include <time.h>typedef struct{ int state[2];//0->red,1->green,交通灯的状态,有南北和东西两组交通灯 int waystate[2];////NS或EW某双方向上正在路口的车辆的个数} shared_sum;
static int semid;//标记信号量集static shared_sum *sharedsum;//创建编号为0~4的个信号量,分别表示四个方向的车在过路口时与同方向的车的互斥0-N,1-S,2-E,3-W
void create()
{
int semnum;
if((semid = semget(IPC_PRIVATE,4,0666))==-1)////创建信号量集
perror("failed to create semaphore");
for(semnum=0;semnum<4;semnum++)
{
if(semctl(semid,semnum,SETVAL,1)==-1)//初始化各信号量 perror("failed to set semaphore");
}
}//开辟共享内存区,存储NS和EW两组红绿灯状态
int shmem(){ int shid; int num; shid = shmget(IPC_PRIVATE,sizeof(shared_sum),IPC_CREAT|0666);//创建内存区 if(shid ==-1) { if(((shid = shmget(IPC_PRIVATE,sizeof(shared_sum),IPC_CREAT|0664))==-1)|| ((sharedsum = (shared_sum *)shmat(shid,NULL,0)) == (void *)-1)) { return -1; } } else { sharedsum = (shared_sum *)shmat(shid,NULL,0);//内存区数据关联 if(sharedsum ==(void *)-1) return -1; sharedsum->state[0] = 0;//NS = green sharedsum->state[1] = 1;//EW = red printf("初始时南北方向为红灯,东西方向为绿灯\n"); sharedsum->waystate[0] = 0;//NS no cars in the corner sharedsum->waystate[1] = 0;//EW no cars in the corner } return 0; }//way 表示一个方向的路,可以是东西南北中的一个值。
void up(int way)
{
struct sembuf v_buf = {way,1,SEM_UNDO};
semop(semid,&v_buf,1);
}
void down(int way)
{
struct sembuf p_buf = {way,-1,SEM_UNDO};
semop(semid,&p_buf,1);
}
//交通灯进程,每3秒换一次void led(){ while(1) { sleep(3); sharedsum->state[0] = 1-sharedsum->state[0];//NS sharedsum->state[1] = 1-sharedsum->state[1];//EW }}void car(int i,int num){ int way ; int j; time_t t; if(i==0||i==1) way = 0;//NS else way = 1;//EW srand((unsigned) time(&t));//初始化随机数发生器
for(j=0;j<5;)//每辆车跑10次,所以最后一次结束比如东西方向绿灯但是只跑了东西各一辆是因为10次到了,不是因为绿灯太短 { down(i); if(sharedsum->state[way] == 1 && sharedsum->waystate[1-way] == 0)//如果该方向绿灯并且与其垂直方向上没车在路口中。
{ if(sharedsum->state[0]==0) printf("南北红灯 "); else printf("南北绿灯 "); if(sharedsum->state[1]==0) printf("东西红灯,"); else printf("东西绿灯,"); switch(i) { case 0: printf("向北第%d号车进路口\n",num+1); sharedsum->waystate[0]++; sleep(1);//过路口的时间设为 1 秒
printf("向北第%d号车过路口\n",num+1); sharedsum->waystate[0]--;break; case 1: printf("向南第%d号车进路口\n",num+1); sharedsum->waystate[0]++; sleep(1); printf("向南第%d号车过路口\n",num+1); sharedsum->waystate[0]--;break; case 2: printf("向东第%d号车进路口\n",num+1); sharedsum->waystate[1]++; sleep(1); printf("向东第%d号车过路口\n",num+1); sharedsum->waystate[1]--;break; case 3: printf("向西第%d号车进路口\n",num+1); sharedsum->waystate[1]++; sleep(1); printf("向西第%d号车过路口\n",num+1); sharedsum->waystate[1]--;break; } j++; } up(i); usleep(rand() % 1000);//随机睡眠0~1秒
} }int main()
{ int i; int num; create();//创建信号量集 if(shmem()==-1)//创建共享内存 { return -1; } if(fork() ==0) { led();//创建交通灯进程 return 0; }
for(num=0;num<4;num++)//每个方向4辆车循环
{ for(i=0;i<4;i++)//四个方向
{ if(fork() == 0) {
car(i,num);//产生i方向,编号为num的车 return 0; } } } for(i=0;i<16;i++)//等待子进程结束 wait();
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -