中易网

按要求用C语言写约瑟夫环

答案:6  悬赏:50  
解决时间 2021-03-15 04:07
C语言高手快来帮帮我啊~ 用C语言按要求写约瑟夫环! (1)问题描述:编号为1,2,…,n的n个人按顺时针方向围坐一圈,每个人持有一个密码(正整数)。一开始任选一个正整数作为报数的上限值m,从第一个人开始按顺时针方向自1开始顺序报数,报到m的人出列,将他的密码作为新的m值,从他在顺时针方向上的下一个人开始重新从1报数,如此下去,直到所有人全部出列为止。设计一个程序求出出列顺序。 (2)基本要求:可以利用单项循环链表存储结构模拟此过程,按照出列的顺序打印出各人的编号和密码。 (3)实现提示:用不带头结点的单循环链表表示一圈人的编号和密码,程序一开始,要求用户指定初始报数的上限,然后依次输入各人的密码。 (4)程序实现:用一个结构体表示每个人的编号和密码,将结构体连起来构成循环单链表。 相信百度里有高手啊~
最佳答案
这没啥高手的,人称入门题目,也就是说,会做这个基本就可以用C做一些东西了。这是我以前写的,从博客上面搞下来的,你试试看能不能运行,我当时似乎是运行过了的。不过这个不是用链表做的,用数组做的,你结合链表的语法把他改一下就行了,很简单的,就一个结构体而已么,反正基本思路这样就对了。另外对了,当时水平有限还不懂动态分配内存,你去查一下malloc函数的用法,觉得合适可以加进去,你用new命令也可以动态分配内存,具体的可以去看看MSDN,MSDN好东西啊。

#include<stdio.h>
#include<stdlib.h>
void main()
{
int a[100];
int n,r,ctor,u;
int call(int a[],int real,int u);

for(n=0;n<=99;n++)a[n]=0;

printf("/约瑟夫环 JOSEPHUS/\n\n");
printf("输入参与报数的人数\n");
scanf("%d",&r);
printf("输入报数上限\n");
scanf("%d",&u);
ctor=1;

for(n=0;n<r;n++)
{
*(a+n)=ctor;
ctor++;
if(ctor>u)ctor=1;
}
call(a,r,u);system("pause");
}

int call(int a[],int real,int u)
{
int n1,i;
int *p;
p=(a+u-1);
n1=0;i=u;

for(;n1<real-1;p++)
{
if(p>(a+real-1))p=a;
if(*(p)!=0)
{
if(i>u)i=1;
if(i==u)
{
*(p)=0;n1++;
}
i++;
}
}

for(i=0;i<real;i++)
if(*(a+i)!=0)printf("所剩最后一位原来的呼号是%d\n\n",i+1);
}

写完了
全部回答
做这个问题很麻烦,分太低了。
刚刚也有人问了,真是巧。我昨天自己还在做数据结构时候也碰到了。所以两个都给你吧 #include<stdio.h> #define N 13 struct person { int number; int nextp; }link[N+1]; void main() { int i,count,h; for(i=0;i<=N;i++) { if(i==N) link[i].nextp=1; else link[i].nextp=i+1; link[i].number=i; } printf("\n"); count=0; h=N; printf("sequence that persons leave the circle:\n"); while (count<N-1) { i=0; while(i!=3) { h=link[h].nextp; if(link[h].number) i++; } printf("%4d",link[h].number); link[h].number=0; count++; } printf("\nThe last one is"); for(i=1;i<=N;i++) if(link[i].number) printf("%3d",link[i].number); printf("\n"); } 数据结构的思路: void Josephus(int n,int m,int s) //使用带表头附加节点的循环单链表为空 { //生成表头附加结点,此时循环单链表为空 LNode* HL=new LNode; HL->next=HL; int i; //生成含n个结点的,结点值依次为1-n的带表头附加结点的循环表 for(i=n;i>=1;i--) //生成新结点 LNode* newptr=new LNode; newptr->data=i; //新结点插入到表头 newptr->next=HL->next; HL->next=newptr; } //从表头开始顺序查找出第s个结点,对应第1个开始报数的人 LNode *ap=HL,*cp=HL->next; for(i=1;i<s;i++){ //ap和cp指针后移一个位置 ap=cp; cp=cp->nextl //若cp指向了表头附加的结点,则仍需后移指针,使之指向表头结点 if(cp==HL){ap=HL;cp=HL->next;} } //依次使n-1个人出列 for(i=1;i<n;i++) //顺序查找出待出列的人,即为循环结束后cp所指向的结点 for(int j=1;j<m;j++) { ap=cp; cp=cp->next; if(cp==HL){ap=HL;cp=HL->next;} } //输出cp结点的值,即出列的人 cout<<cp->data<<" "; //从单链表中删除结点的后继结点 cp=ap->next; //若cp指向了表头附加结点,则后移ap和cp指针 if(cp==HL){ap=HL;cp=HL->next;} } //使最后一个人出列 cout<<HL->next->data<<endl; //删除表头结点和表头附加结点 delete HL->next; delete HL; }
我用的双向循环链表写的 因为这样比较容易解决一些特殊情况 随机数的上线我设置的是小于起始时的人数 大了也没有什么意义 无非多转几圈 反而不好验证 以前就打算写这个程序 一直没时间 这段时间正好复习一下数据结构 顺便写一些这方面的程序 #include"stdio.h" #include"windows.h" #include"malloc.h" #include"time.h" #define N 10 typedef struct node { int num ; int sec ; struct node *pre; struct node *next; }body; void Initiate(body *x); void Delect(int x,body *head); void main() { int m; body *first; first=(body *)malloc(sizeof(body)); first->next=first; first->pre=first; Initiate(first); m=rand()%(N-1); m=m+1; printf("\n任意数m=%d\n",m); Delect(m,first); } void Initiate(body *head) { int xx[N],yy[N]; int i; body *p,*q; for(i=0;i<N;i++) yy[i]=i+1; srand( time(NULL) ); for(i=0;i<N;i++) xx[i]=yy[rand()%N]; head->num=yy[0]; head->sec=xx[0]; for(i=1;i<N;i++) { p=head; q=(body *)malloc(sizeof(body)); q->num=yy[i]; q->sec=xx[i]; while(p->next!=head) p=p->next; p->next=q; q->pre=p; q->next=head; head->pre=q; } printf("序号:"); for(i=0;i<N;i++) printf("%2d ",i+1); printf("\n密码:"); for(i=0;i<N;i++) printf("%2d ",xx[i]); } void Delect(int x,body *head) { body *p; p=head; int i=1,sec; while(i<x && p->next!=p) {p=p->next;i++;} if(p->next!=p) { sec=p->sec; printf("序号: %2d 密码: %2d \n",p->num,p->sec); p=p->pre; p->next=p->next->next; p->next->pre=p; head=p->next; Delect(sec,head); } else { printf("序号: %2d 密码: %2d \n",p->num,p->sec); printf("\n问题结束!\n"); } }
我刚做啊!!!!!!!!!! #include<stdio.h> #include<malloc.h> typedef struct node { int date; int number; struct node *next; }ListNode; ListNode *createlist(int n,int a[]) { int j; ListNode *head=(ListNode *)malloc(sizeof(ListNode)); ListNode *s,*r=head; for(j=1;j<=n;j++) { s=(ListNode *)malloc(sizeof(ListNode)); s->date=a[j]; s->number=j; r->next=s; r=s; } r->next=head->next; free(head); return r; } void getnode(ListNode *head) { int m,k,i; ListNode *p,*r; p=head; printf("输入上限值的初值 :"); scanf("%d",&m); printf("出列顺序 :"); if(m>0) { while(p->next!=p) { for(k=1;k<m;k++) p=p->next; printf("%d ",p->next->number); m=p->next->date; r=p->next; p->next=r->next; free(r); } printf("%d",p->number); free(p); printf("\n"); } } void main() { ListNode *ha; int a[100],n,i; printf("输入人数 :"); scanf("%d",&n); printf("输入密码 :"); for(i=1;i<=n;i++) scanf("%d",&a[i]); ha=createlist(n,a); getnode(ha); printf("\n"); }
#include <stdio.h> #include <malloc.h> struct node { int num;//为方便表达,每个节点拥有一个序号 int password;//密码 struct node *next; }; node * creatlist(int people)//构造链表 { int i=1;//序号 int _password; node *r,*s; node *L=(node *)malloc(sizeof(node));//创造头结点 r=L; while(i<=people) { printf("请输入第%d个人的密码:",i); scanf("%d",&_password); s=(node *)malloc(sizeof(node)); s->num=i; s->password=_password; r->next=s; r=s; i++; } r->next=L;//循环链表 return L; } void getoutseq(node *L,int firstp)//计算出列顺序并输出的函数 { int _password=firstp; node *p=L; node *r=L;//r为p的前驱节点 int i=1; while(L->next!=L)//当L为非空表时一直循环,空表表示所有人已经出列,则退出循环 { while (i<=_password)//根据密码移动指针 { if (p->next!=L)//当p的下一个节点非头结点,直接向下移 { r=p;//p移动前先备份 p=p->next; } else//当p的下一个节点是头节点,则令p指向一号节点 { r=L; p=L->next; } i++; } printf("%d号出列\n",p->num); _password=p->password;//获取节点中的密码 r->next=p->next;//删除并释放p free(p); i=1; p=r; } printf("结束!\n"); } int main() { node *list; int people; int firstp; printf("请输入人数:"); scanf("%d",&people); putchar('\n'); printf("请输入初始密码:"); scanf("%d",&firstp); putchar('\n'); list=creatlist(people); getoutseq(list,firstp); printf("按确定键退出。。。"); getchar(); getchar(); return 0; }
我要举报
如以上问答内容为低俗、色情、不良、暴力、侵权、涉及违法等信息,可以点下面链接进行举报!
大家都在看
女孩子,叫桐雨好不好?怎么解释?
百世汇通宝泉岭分公司这个地址在什么地方,我
用鼻呼吸比用口好,下面不能成立的理由是( 
岁月静好,愿时光待你如初 请问翻译成法语是
小学必背的课文有哪些?
生意好不好是不是跟市场行情不好了 还是跟命
已过如山看不见,人过如丝看分明是什么意思?
家里房子坐北朝南,在大门口正前面三到五米再
可露现烤烘焙我想知道这个在什么地方
为什么不能在58同城里买卖手机号了?
为什么说五月归来不看山,黄山归来不看岳
守护甜心中唯世君他们的King's chair Qu
怎么查询SIM卡的号码``卡里没钱,朋友也不知道
复合木板与实木地板哪个好。
在一个三角形中其中一个锐角是80度减去这个角
推荐资讯
为什么我的笔记本一玩游戏就死机?高手来
宋茜2015回国发展,还会在韩国活动吗
枣洼在什么地方啊,我要过去处理事情
谁知道北京市朝阳区香河园街道西坝河东里幼儿
南口机车车辆机械厂单身公寓地址在哪,我要去
找一张魔兽争霸的地图
打卡机导出用户数据时出现数据类型不匹配怎么
mp3的格式现在是MB怎样转换成KB 请哪位指点一
大家说说:是南方人才多还是北方人才多
小区宽带的总线,路由器,交换机一般都在哪啊
基督教会学校是一所什么样的学狡
无锡硕放飞达车行地址在哪,我要去那里办事
手机登qq时,显示手机磁盘不足,清理后重新登
刺客的套装怎么选啊?