生产者程序与流图.docx

上传人:b****3 文档编号:27411252 上传时间:2023-06-30 格式:DOCX 页数:11 大小:118.19KB
下载 相关 举报
生产者程序与流图.docx_第1页
第1页 / 共11页
生产者程序与流图.docx_第2页
第2页 / 共11页
生产者程序与流图.docx_第3页
第3页 / 共11页
生产者程序与流图.docx_第4页
第4页 / 共11页
生产者程序与流图.docx_第5页
第5页 / 共11页
点击查看更多>>
下载资源
资源描述

生产者程序与流图.docx

《生产者程序与流图.docx》由会员分享,可在线阅读,更多相关《生产者程序与流图.docx(11页珍藏版)》请在冰豆网上搜索。

生产者程序与流图.docx

生产者程序与流图

生产者程序与流图

 

 

————————————————————————————————作者:

————————————————————————————————日期:

 

程序代码:

#include//定义头文件

#include

#include

#include

#include

#include

#definePRODUCER2//宏定义生产者个数,2个

#defineCOSTOMER3//宏定义消费者个数,3个

#defineWRITE_NUM6//宏定义写缓冲次数,6次

#defineREAD_NUM4//宏定义读缓冲次数,4次

 

#defineSEM_ALL_KEY1342

#defineSEM_EMPTY0

#defineSEM_FULL1

#defineBUF_LENGTH(sizeof(structcontainer_buffer))//宏定义缓冲区大小

#defineBUFFER_NUM3//宏定义缓冲区个数,3个

#defineSHM_MODE0600//宏定义创建和访问标志

 

//缓冲区结构(循环队列)

structcontainer_buffer//定义共享缓冲区结构

{

charletter[BUFFER_NUM];

inthead;

inttail;

intis_empty;//判断缓冲区是否为空的标志

};

//得到6以内的一个随机数,产生延迟时间

intrandom_num()

{

intt;

srand((unsigned)(getpid()+time(NULL)));

t=rand()%6;

returnt;

}

//P操作,获得使用权

voidp(intsem_id,intsem_num)

{

structsembufsem_buff;

sem_buff.sem_num=sem_num;

sem_buff.sem_op=-1;

sem_buff.sem_flg=0;

semop(sem_id,&sem_buff,1);

}

//得到一个随机字符,模拟产品名字

charrandom_letter()

{

chara;

srand((unsigned)(getpid()+time(NULL)));

a=(char)((char)(rand()%15)+'!

');

returna;

}

 

//V操作,释放使用权

voidv(intsem_id,intsem_num)

{

structsembufsem_buff;

sem_buff.sem_num=sem_num;

sem_buff.sem_op=1;

sem_buff.sem_flg=0;

semop(sem_id,&sem_buff,1);

}

//主函数

intmain(intargc,char*argv[])

{

intshm_id,sem_id;//定义共享内存段标识变量shm_id,定义信号量标识变量sem_id

intnum_p=0,num_c=0,i,j;//定义生产者和消费者的个数变量,初始化为0

structcontainer_buffer*shmptr;//指向缓冲区结构的指针

charpn;//随机字符,代表产品

time_tnow;//时间变量

pid_tpid_p,pid_c;//进程pid变量

printf("Mainprocessstarts.\n");

sem_id=semget(SEM_ALL_KEY,2,IPC_CREAT|0660);//创建两个信号量,empty,full

semctl(sem_id,SEM_EMPTY,SETVAL,BUFFER_NUM);//索引为SEM_EMPTY的信号量值为3

semctl(sem_id,SEM_FULL,SETVAL,0);//索引为SEM_FULL的信号量值为0

if((shm_id=shmget(IPC_PRIVATE,BUF_LENGTH,SHM_MODE))<0)//申请一个共享主存段,大小为缓冲区大小

{

exit

(1);//失败退出

}

if((shmptr=shmat(shm_id,0,0))==(void*)-1)//将共享段与进程相连

{

exit

(1);//失败退出

}

shmptr->head=0;//初始化缓冲区

shmptr->tail=0;

shmptr->is_empty=1;

while((num_p++)

{

if((pid_p=fork())<0)//创建一个进程

{

exit

(1);//失败退出

}

//如果是子进程,开始创建生产者

if(pid_p==0)

{

if((shmptr=shmat(shm_id,0,0))==(void*)-1)//将共享段与本进程相连

{

exit

(1);//失败退出

}

for(i=0;i

{

p(sem_id,SEM_EMPTY);//p操作,申请使用权,p(empty)

sleep(random_num());//随机等待一段时间

shmptr->letter[shmptr->tail]=pn=random_letter();//在缓冲队列里面放入一个产品

shmptr->tail=(shmptr->tail+1)%BUFFER_NUM;

shmptr->is_empty=0;//更新缓冲区状态为满

now=time(NULL);//取得系统时间

printf("currenttime:

%02d:

%02d:

%02d\t",localtime(&now)->tm_hour,localtime(&now)->tm_min,localtime(&now)->tm_sec);

for(j=(shmptr->tail-1>=shmptr->head)?

(shmptr->tail-1):

(shmptr->tail-1+BUFFER_NUM);!

(shmptr->is_empty)&&j>=shmptr->head;j--)

//输出缓冲区状态

{

printf("%c",shmptr->letter[j%BUFFER_NUM]);

}

printf("\tProducer%dputsaproductnamedas'%c'.\n",num_p,pn);//输出动作序列

fflush(stdout);//清除文件缓存区

v(sem_id,SEM_FULL);//释放对文件的使用权,V(full)

}

shmdt(shmptr);//将共享段与进程之间解除链接

exit(0);//子进程终止

}

}

for(;num_c

{

if((pid_c=fork())<0)//创建一个子进程

{

printf("Erroronfork.\n");

exit

(1);//失败退出

}

//如果是子进程,开始创建消费者

if(pid_c==0)

{

if((shmptr=shmat(shm_id,0,0))==(void*)-1)//将共享段与本进程相连

{

printf("Erroronshmat.\n");

exit

(1);//失败退出

}

for(i=0;i

{

p(sem_id,SEM_FULL);//p操作,p(full),实现同步

sleep(random_num());//随机等待一段时间

pn=shmptr->letter[shmptr->head];//得到读取的产品标示字符

shmptr->head=(shmptr->head+1)%BUFFER_NUM;

shmptr->is_empty=(shmptr->head==shmptr->tail);//更新缓冲区产品状态

now=time(NULL);//得到系统时间

printf("currenttime:

%02d:

%02d:

%02d\t",localtime(&now)->tm_hour,localtime(&now)->tm_min,localtime(&now)->tm_sec);

for(j=(shmptr->tail-1>=shmptr->head)?

(shmptr->tail-1):

(shmptr->tail-1+BUFFER_NUM);!

(shmptr->is_empty)&&j>=shmptr->head;j--)

//输出缓冲区状态

{

printf("%c",shmptr->letter[j%BUFFER_NUM]);

}

printf("\tConsumer%dgetsaproductnamedas'%c'.\n",num_c,pn);

fflush(stdout);//清除文件缓存区

v(sem_id,SEM_EMPTY);

}

shmdt(shmptr);//解除共享段与本进程的连接

exit(0);

}

}

//主控程序最后退出

while(wait(0)!

=-1);//等待子进程结束

shmdt(shmptr);//接触父进程和共享段的连接

shmctl(shm_id,IPC_RMID,0);//删除共享内存段

semctl(sem_id,IPC_RMID,0);

printf("Mainprocessends.\n");

fflush(stdout);//清除文件缓存区

exit(0);

}

 

生产者流程图:

 

消费者流程图:

 

主程序流程图:

运行结果如下:

 

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 总结汇报 > 学习总结

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1