约瑟夫环循环链表

//约瑟夫环问题的一种描述是:编号为1,2,3,n的n个人按顺时针围坐一圈,每人持有一个密码(正整数),一开始任选一个正整数作为报数上限值m,从第一个人开始按顺时针方//向自1开始报数,报到m时停止报数,报m的人出列,将他的密码作为新的m值,从他在顺时针方向上的下一个人开始重新从1报数,如此下去,直至所有人出列为止。试设计///一个程序求出列顺序.

//测试数据:m的初值为20,n=7,7个人的密码依次为:3,1,7,2,4,8,4,首先m值为6,正确的顺序应是6,1,4,7,2,3,5.

 #include<stdio.h>

 

#include<malloc.h>

 

typedef struct node

{

 

     int number;

     int key;

     struct node* next;

 

}listnode, * circularlist;//定义了结点类型listnode和指针类型circularlist

 

int main()

{

 

       int amount,t,code,m,k;// amount表示总人数,code表示相应的学生密码

       circularlist w=(listnode*)malloc(sizeof(listnode));

       w->next=w;//循环链表仅一个元素时依然满足

       listnode *v;

       printf("请输入总人数:");

       scanf("%d",&amount);

       v=w;

 

       for(k=1;k<=amount;k++)

      {

 

              printf("请输入第 %d学生的密码: ",k);

              scanf("%d",&code);

              w->key=code;

              w->number=k;

              if(k!=amount)

              {

                    w->next=(listnode*)malloc(sizeof(listnode));

                    w=w->next;

              }

 

             w->next=v;

 

        }//循环结束后自动生成链表头

 

       printf("约瑟夫环已建成,可以开始!\n");

 

       printf("请输入初值: ");

 

       scanf("%d",&m);

 

       if(m<=0)

      {

             printf("输入错误,请重新输入\n");

             return(1);

      }

 

       m=m-1;//使w提前停下

 

       printf("出列顺序是: ");

 

       //w为起始点

 

       do

      {

              t=0;//加入m1后为零的情况

              while(t!=m)

             {

                   w=w->next;

                      t++;

             }

 

               v=w->next;

                w->next=v->next;

                printf(" %d",v->number);

                  m=v->key;

                m=m-1;

                  free(v);//释放v的存储空间

      }while(w->next!=w);

 

       printf(" %d\n",w->number);

       free(w); //释放w的存储空间

       getchar();

       getchar();

       return(0);

 

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值