/*题目:一群哲学家围坐在一个圆桌,手上持有密码m,并从1开始编了号取初值m,哲学家从1开始报数, 报到m的哲学家停止吃饭,退出圆桌,求哲学家退出的顺序。要求:n和初值m由完家输入.手上的密码随机产生.最后要打印出编号对应的密码,输出哲学家离开的相后顺序 分析:可用循环链表实现,链表数据类型为结构体,记录编号和相应密码,另外设标志哲学家报数的变量mouth, 它的值和哲学家嘴上报的数相等,则如果mouth和m相等,该哲学家就应该离开离开前取他的密码交给m,同时将他的编号放另一单链表numbsave保存。注意编号要从numbsave的最后节点插入。当循环链表指向自身时停止比较,这个哲学家即是最后离开的一个.依次打印出numbsave中的数即为按编号哲学家离开的先后顺序。 */ #include "stdio.h" #include "conio.h" #include "stdlib.h" struct philosopher /*哲学家就餐结构体*/ { int number; /*编号*/ int password; int mouth; /*嘴上报的数*/ struct philosopher *next; }; struct philosopher *phead,*pend,*pp; struct numbsave /*存放离开顺序*/ { int numsave; struct numbsave *next; }; struct numbsave *top=NULL,*numbnew,*numbthis; void main(void) { char *p,d; int b=1,k,n,m,mouthm=1; clrscr(); gotoxy(9,8); printf("please input n m:"); scanf("%d%d",&n,&m); /*n为哲学家人数,m为初始密码*/ phead=(struct philosopher *)malloc(sizeof(struct philosopher)); pend=phead;phead->mouth=1; for(b=1;b<=n-1;b++) /*给哲学家分配随机密码*/ {pend->number=b; k=random(20); /*k为0<k<20之间的数*/ while(k<=0) k=random(20); pend->password=k; pp=(struct philosopher *)malloc(sizeof(struct philosopher)); pend->next=pp; pend=pp; } pend->number=b; /*最后一位哲学家*/ k=random(20); while(k<=0) k=random(20); pend->password=k; pend->next=phead; /*形成循环链表*/ printf("/n/tphilosopher number correspondence password as followed:/n/t"); pp=phead; for(b=1;b<=n;b++) {printf("%d:%d/t",pp->number,pp->password); pp=pp->next; } while(pend->next!=pend) {if(phead->mouth==m) /*如果嘴上报数和m相等,意味着一个人要走了*/ {pp=phead; phead->next->mouth=1; mouthm=1; /*下一位哲学家从一开始报,mm用于将顺序报出数的交给嘴巴*/ phead=pend->next=phead->next; /*两个指针一定要相邻*/ numbnew=(struct numbsave*)malloc(sizeof(struct numbsave)); m=pp->password; /*修改m的值为离开哲学家的password*/ numbnew->numsave=pp->number; if(top==NULL) {top=numbnew; top->next=NULL;} /*离开的哲学家的编号存入numbsave的最后节点*/ else { numbthis=top; while(numbthis->next!=NULL) numbthis=numbthis->next; numbthis->next=numbnew; numbnew->next=NULL; } free(pp); } else {pend=pend->next; phead=phead->next; /*让phead指向下一个*/ mouthm++; phead->mouth=mouthm; /*嘴巴说我该报mouthm*/ } } /*打印离桌顺序*/ printf("/n/tphilosopher away from cookdesk in the follow queue:/n/t"); while(top!=NULL) { printf("%d ",top->numsave); top=top->next; } printf("%d ",pend->number); /*这个千万别忘了,他是运气最好的一位*/ printf("/n/tpress any key to go back......"); while(!kbhit()) ; } |