鱼C论坛

 找回密码
 立即注册
查看: 10084|回复: 18

[技术交流] 约瑟夫问题(约瑟夫环)

[复制链接]
发表于 2012-12-25 21:46:15 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
题目:用循环链表模拟约瑟夫问题,把41个人自杀的顺序编号输出。

故事情节:

据说著名犹太历史学家 Josephus有过以下的故事:在罗马人占领乔塔帕特后,39个犹太人与Josephus及他的朋友躲到一个洞中,39个犹太人决定宁愿死也不要被敌人抓到,于是决定了一个自杀方式,41个人排成一个圆圈,由第1个人开始报数,每报数到第3人该人就必须自杀,然后再由下一个重新报数,直到所有人都自杀身亡为止。然而Josephus和他的朋友并不想遵从,Josephus要他的朋友先假装遵从,他将朋友与自己安排在第16个与第31个位置,于是逃过了这场死亡游戏。

视频讲解:http://blog.fishc.com/1959.html


源代码参考:http://bbs.fishc.com/thread-25337-1-1.html

小甲鱼最新课程 -> https://ilovefishc.com
发表于 2013-6-28 16:55:39 | 显示全部楼层
本帖最后由 兢兢 于 2013-7-4 02:44 编辑

[人数] = 100
[数数] = 3
Dim b()
ReDim b([人数])
For i=1 to [人数]
   b(i) = 1
Next
i=1
n = [人数]
m=1
While (n > 1)
    While (i<=[人数])
    If b(i) =1 Then
        If m mod [数数] = 0 Then
            b(i)=0
           n = n - 1
          s=s & "→" & i
         End If
        m = m + 1
    End If
    i = i + 1
Wend
i = 1
Wend
msgbox s,vbokonly,"排除顺序"
For i = 1 To [人数]  '查找最后一个数字
        If b(i) = 1 Then
                msgBox  "最后剩下的数是" & i,vbokonly,"约瑟夫环"
        End If
Next
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2013-7-4 19:23:13 | 显示全部楼层
强烈支持楼主ing……
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2013-9-15 00:57:10 | 显示全部楼层

谢谢楼主分享
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2013-12-26 12:41:56 | 显示全部楼层
强烈支持楼主ing……我真的很感悟……
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2013-12-26 12:42:49 | 显示全部楼层
真是难得给力的帖子啊。我只说两句……
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2014-2-20 20:58:03 | 显示全部楼层
强烈支持楼主ing……
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2014-2-21 23:38:53 | 显示全部楼层
强烈支持楼主ing……
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2014-11-6 15:48:57 | 显示全部楼层
支持楼主
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2014-12-3 11:28:46 | 显示全部楼层
强烈支持楼主ing……
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2014-12-27 11:12:59 | 显示全部楼层

强烈支持楼主ing……
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2015-10-30 17:13:43 | 显示全部楼层
强烈支持楼主ing……
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 1 反对 0

使用道具 举报

发表于 2016-1-23 11:39:57 | 显示全部楼层
  1. /*编号为1~N的N个人按顺时针方向坐一圈,每个人持有一个密码(正整数,可以自由输入),
  2. 开始人选一个正整数作为报数上限值M,从第一个人按顺时针方向自1开始顺序报数,报到M时
  3. 停止报数。报M的人出列,将他的密码作为新的M值,从他顺时针方向上的下一个人开始从1报数,
  4. 如此下去,直至所有人出列*/
  5. #include<stdio.h>
  6. #include<stdlib.h>

  7. typedef struct circular_linked_list{
  8.         int password;
  9.         int index;
  10.         struct  circular_linked_list *next;
  11. } Node;

  12. Node * Creat (int n);

  13. int main()
  14. {
  15.         int i,n,m;
  16.         Node *p, *temp;
  17.         printf("输入一个正整数n,代表有n个人围成一个圈。\n");
  18.         scanf("%d",&n);
  19.         p=Creat(n);
  20.         printf("输入一个正整数M,代表第一个人报数的上限值。\n");
  21.         scanf("%d",&m);

  22.     m=m>n?m%n:m;
  23.         while(p->next!=p)
  24.         {
  25.                 for(i=1;i<m-1;i++)
  26.                         p=p->next;
  27.                 printf("%d->",p->next->index);
  28.                 m=p->next->password;
  29.         m=m>n?m%n:m;
  30.                 temp=p->next;
  31.                 p->next=temp->next;
  32.                 free(temp);
  33.                 p=p->next;
  34.         }
  35.         return 0;
  36. }
  37. Node *Creat(int n)
  38. {
  39.         int i;
  40.         Node *head, *p, *s;
  41.         head = (Node *)malloc(sizeof(Node));
  42.         p=head;
  43.         printf("输入N个正整数,代表每个人手中的密码\n");
  44.         for(i=0;i<n;i++)
  45.         {
  46.                 s=(Node *)malloc(sizeof(Node));
  47.                 scanf("%d",&s->password);
  48.                 s->index=i+1;
  49.                 p->next=s;
  50.                 p=s;
  51.         }
  52.         s->next=head->next;
  53.         free(head);
  54.         return s->next;
  55. }
复制代码
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2016-9-10 15:46:43 | 显示全部楼层
感谢楼主
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2016-9-10 16:03:45 | 显示全部楼层
感谢楼主啊
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2017-5-11 09:41:56 | 显示全部楼层
每人持有密码的高级约瑟夫环代码用循环链表实现:
  1. #include<stdio.h>
  2. #include<stdlib.h>
  3. #define NUM 10
  4. #define START 2
  5. struct Date
  6. {
  7.     int number;
  8.     int password;
  9.     struct Date *next;
  10. };

  11. void ListInsert(struct Date **pt,int num,int pass)
  12. {
  13.     struct Date *tmp=NULL,*middle=NULL;
  14.     tmp=(struct Date *)malloc(sizeof(struct Date));
  15.     if(tmp==NULL)   exit(1);
  16.     tmp->number = num;
  17.     tmp->password = pass;
  18.     if((*pt)!=NULL)
  19.     {       
  20.         middle = *pt;
  21.         *pt = tmp;
  22.         tmp->next = middle;
  23.     }
  24.     else
  25.     {
  26.         tmp->next=NULL;
  27.         (*pt)=tmp;
  28.     }
  29. //    printf("插入成功!\n");
  30. }

  31. void ListPrint(struct Date *pt)
  32. {
  33.     while(pt!=NULL)
  34.     {
  35.             printf("%d--%d\n",pt->number,pt->password);
  36.         pt = pt->next;
  37.     }
  38.     putchar('\n');
  39. }
  40. void ListCircle(struct Date **pt)
  41. {
  42.     struct Date *rear=*pt;
  43.     while(rear->next!=NULL)
  44.         rear=rear->next;
  45.     rear->next=*pt;
  46. }

  47. void JosephusHard(struct Date *pt)
  48. {
  49.     struct Date *kill,*previous;
  50.     unsigned code=START;
  51.     int i=0,FLAG=0;
  52.     printf("kill game start!\n");
  53.     printf("start code is: %d\n\n",START);   

  54.     while((pt->next)!=pt)
  55.     {
  56.         if(code<1)
  57.         {
  58.             printf("the code is error\n");
  59.             exit(1);
  60.         }
  61.         else if(code==1)
  62.         {
  63.             FLAG=1;
  64.             goto specialsec;
  65.         }
  66.         else if(code==2)
  67.         {
  68.              ;   
  69.         }
  70.         else
  71.         {
  72.                 for(i=code-2;i>0;--i)
  73.                     pt=pt->next;
  74.         }
  75.         kill=pt->next;
  76.         code=kill->password;
  77.         pt->next=kill->next;
  78.         printf("kill No.%d\t",kill->number);
  79.         printf("next code is %d\n\n",code);
  80.         free(kill);
  81.         pt=pt->next;

  82. specialsec:
  83.         if(FLAG)
  84.         {
  85.             FLAG=0;        //重置FLAG
  86.             previous=pt;
  87.             while(previous->next!=pt)
  88.             {
  89.                 previous=previous->next;       
  90.             }
  91.             kill=pt;            
  92.             pt=previous;
  93.             code=kill->password;
  94.             pt->next=kill->next;
  95.             printf("kill No.%d\n",kill->number);
  96.             printf("next code is %d\n",code);
  97.             free(kill);
  98.             pt=pt->next;
  99.         }


  100.    
  101.     }
  102.     printf("kill game over, No.%d survive!\n",pt->number);

  103. }

  104. int main()
  105. {
  106.     struct Date *pt=NULL;
  107.     for(int i=NUM ;i>0;i--)
  108.         ListInsert(&pt,i, NUM+1-i);
  109.     ListPrint(pt);
  110.     ListCircle(&pt);

  111.     JosephusHard(pt);
  112.     return 0;
  113. }
复制代码
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2017-10-18 18:05:07 | 显示全部楼层
  1. # Python 3
  2. number = int(input("Game number:"))
  3. people = []
  4. for i in range(number):
  5.     people += [[i - 1, i + 1, i + 1]]
  6. people[0][0], people[number - 1][2] = number - 1, 0

  7. flag = 0
  8. for deadnumber in range(number - 2):
  9.     for j in range(2):
  10.         flag = people[flag][2]
  11.     temp = people[flag]
  12.     temp2 = temp[2]
  13.     people[temp[0]][2] = temp[2]
  14.     people[temp[2]][0] = temp[0]
  15.     people[flag] = [0, 0, 0]
  16.     flag = temp2

  17. print(people[flag][1], people[people[flag][2]][1])
复制代码
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2018-1-29 21:11:16 | 显示全部楼层
本帖最后由 圣狄雅哥 于 2018-1-29 21:12 编辑

学习了
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-9-20 10:42:47 | 显示全部楼层
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2025-6-8 02:59

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表