如何用循环链表来求解Josephu问题

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

我用C++实现了Josephu问题,从输出结果看,应该是正确的,如果有错误,欢迎大家不吝指出,谢谢。

#include <cstdio>                                                                                                                   
#include <cstdlib>                                                                                  
                                                                                                    
typedef struct node {                                                                               
    int value = -1;                                                                                 
    struct node *next = nullptr;                                                                    
} Node, *NodeList;                                                                                  
                                                                                                    
NodeList build(int n)                                                                               
{                                                                                                   
    NodeList head = nullptr, pre = nullptr;                                                         
    for (int i = 0; i < n; ++i) {                                                                   
        NodeList cur = (NodeList)calloc(sizeof(Node), sizeof(char));                                
        cur->value = i;                                                                             
        if (!head) head = cur;                                                                      
        if (pre && !pre->next) pre->next = cur;                                                     
        pre = cur;                                                                                  
        //printf("create: %d\n", i);                                                                
    }                                                                                               
    pre->next = head;                                                                               
                                                                                                    
    return head;                                                                                    
}                                                                                                   
                                                                                                    
void dump(NodeList head, int size)                                                                  
{                                                                                                   
    int num {0};                                                                                    
    for (NodeList cur = head; cur; cur = cur->next) {                                               
        if (num == size) break;                                                                     
        printf("list node: %d\n", cur->value);                                                      
        ++num;                                                                                      
    }                                                                                               
}                                                                                                   
                                                                                                    
void josephus(int n, int k, int m)                                                                  
{                                                                                                   
    NodeList head = build(n);                                                                       
    //dump(head, n);                                                                                
                                                                                                    
    int size = n;                                                                                   
    int skip {1}, out {1};                                                                          
    for (NodeList pre = nullptr, cur = head; cur; pre = cur, cur = cur->next) {                     
        if (skip < k) {                                                                             
            printf("size: %d, num: %d, skip: %d\n", size, cur->value, skip);                        
            ++skip;                                                                                 
            continue;                                                                               
        }                                                                                           
                                                                                                    
        if (out < m) {                                                                              
            printf("size: %d, num: %d, count_off: %d\n", size, cur->value, out);                    
            ++out;                                                                                  
            continue;                                                                               
        }                                                                                           
                                                                                                    
        printf("number node %d out list~!\n", cur->value);                                          
        pre->next = cur->next;                                                                      
        free(cur);                                                                                  
        cur = pre;                                                                                  
        skip = out = 1;                                                                             
                                                                                                    
        --size;                                                                                     
        if (!size) break;                                                                           
    }                                                                                               
                                                                                                    
}                                                                                                   
                                                                                                    
int main()                                                                                          
{                                                                                                   
    josephus(10, 3, 2);                                                                             
}

运行结果:

$ ./Circylar_linked_lists 
size: 10, num: 0, skip: 1
size: 10, num: 1, skip: 2
size: 10, num: 2, count_off: 1
number node 3 out list~!
size: 9, num: 4, skip: 1
size: 9, num: 5, skip: 2
size: 9, num: 6, count_off: 1
number node 7 out list~!
size: 8, num: 8, skip: 1
size: 8, num: 9, skip: 2
size: 8, num: 0, count_off: 1
number node 1 out list~!
size: 7, num: 2, skip: 1
size: 7, num: 4, skip: 2
size: 7, num: 5, count_off: 1
number node 6 out list~!
size: 6, num: 8, skip: 1
size: 6, num: 9, skip: 2
size: 6, num: 0, count_off: 1
number node 2 out list~!
size: 5, num: 4, skip: 1
size: 5, num: 5, skip: 2
size: 5, num: 8, count_off: 1
number node 9 out list~!
size: 4, num: 0, skip: 1
size: 4, num: 4, skip: 2
size: 4, num: 5, count_off: 1
number node 8 out list~!
size: 3, num: 0, skip: 1
size: 3, num: 4, skip: 2
size: 3, num: 5, count_off: 1
number node 0 out list~!
size: 2, num: 4, skip: 1
size: 2, num: 5, skip: 2
size: 2, num: 4, count_off: 1
number node 5 out list~!
size: 1, num: 4, skip: 1
size: 1, num: 4, skip: 2
size: 1, num: 4, count_off: 1
number node 4 out list~!

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值