• 数据结构设计——约瑟夫双向生死游戏


    约瑟夫双向生死游戏

    [问题描述]:

    约瑟夫双向生死游戏是在约瑟夫生者死者游戏的基础上,正向计数后反向计数,然后再正向计数。

    具体描述如下:30个旅客同乘一条船,因为严重超载,加上风高浪大,危险万分;因此船长告诉乘客,只有将全船一半的旅客投入海中,其余人才能幸免遇难。无奈,大家只得同意这种办法,并议定30个人围成一圈,由第一个人开始,顺时针依次报数,数到第9人,便把他投入大海中,然后从他的下一个人数起,逆时针数到第5人,将他投入大海,然后从他逆时针的下一个人数起,顺时针数到第9人,再将他投入大海,如此循环,直到剩下15个乘客为止。问哪些位置是将被扔下大海的位置。

    [设计思路]:

    本游戏的数学建模如下:假设n个旅客排成一个环形,依次顺序编号12,…,n。从某个指定的第1号开始,沿环计数,数到第m个人就让其出列,然后从第m+1个人反向计数到m-k+1个人,让其出列,然后从m-k个人开始重新正向沿环计数,再数m个人后让其出列,然后再反向数k 个人后让其出列。这个过程一直进行到剩下q个旅客为止。 也就是一个双向循环链表,分别进行正向移动和反向移动,出列相应位置的人

    实现:

    (1) 输入旅客的个数,也就是n的值;

    (2)正向离开旅客的间隔数,也就是m的值;

    (3) 反向离开旅客的间隔数,也就是k的值;

    (4) 输出出列的人所在的位置

    #include<stdio.h>
    #include<string.h>
    #include<stdlib.h>
    
    typedef struct LinkList{
        int data;
        struct LinkList *pri;
        struct LinkList *next;
    }LinkList;
    
    //尾插入法建立链表   链表的头结点head作为返回值
    LinkList  *create_LinkListWEI(int n)
    {
        LinkList *head, *p, *q;
        head = p =(LinkList*)malloc(sizeof(LinkList));
        p->pri = NULL;
        int i = 2;// 位置
        p->data = 1;
        n--;
        while(n--){
            q = (LinkList  *)malloc(sizeof(LinkList));
            q->data = i;
            q->next = NULL;
            p->next = q;
            q->pri = p;
            p = q;
            i++;
        }
        q->next = head;
        head->pri = q;
        return head;
    }
    
    void print(LinkList *head,int n){
        printf("
    正向:
    ");
        LinkList *p = head;
        int num = 0;
        while(p->next){
            printf("%d ",p->data);
            p = p->next;
            num++;
            if(num >= n)
                break;
        }
        num = 0;
        printf("
    反向:
    ");
        p = head;
        while(p->pri){
            printf("%d ",p->pri->data);
            p = p->pri;
            num++;
            if(num >= n)
                break;
        }
        printf("
    ");
    }
    
    LinkList  *kill_m(LinkList *head,int m){
        LinkList *p = head;
        LinkList *q;
        int time = 1;
        while(p->next){
            q = p->next;
            if(time == m){
                printf("%d ",p->data);
                //删除链表结点 p
                p->pri->next = q;
                q->pri = p->pri;
                return q;
            }
            p = p->next;
            time++;
        }
    
    }
    
    LinkList  *kill_k(LinkList *head,int k){
        LinkList *p = head;
        LinkList *q;
        int time = 1;
        while(p->pri){
            q = p->pri;
            if(time == k){
                printf("%d ",p->data);
                //删除链表结点 p
                q->next = p->next;
                p->next->pri = q;
                return q;
            }
            p = p->pri;
            time++;
        }
    }
    
    int main(){
        int all,m,k;
        /*
        m 正向    k 反向
        */
        scanf("%d %d %d",&all,&m,&k);
        LinkList *p,*q;
        p = create_LinkListWEI(all);
        printf("双向链表的构建:
    ");
        print(p,all);
        printf("
    ");
        // 杀人
        int flag = 1;
        int re = all / 2;
        q = p;
        printf("
    被踢下船的人所在位置:
    ");
        while(all > re){
            if(flag == 1)
                q = kill_m(q,m);
            else
                q = kill_k(q,k);
            //printf("
    q->data:%d
    ",q->data);
            flag *= -1;
            all--;
        }
        return 0;
    }

  • 相关阅读:
    事件溯源的使用实例
    CQRS With Axon
    maven打包带依赖
    MongoDB Query语法和工具
    docker 在外部指定参数变量 spring
    logger 过滤部分类的logger
    Nginx ServerName指令
    Nginx 处理Http请求简单流程
    Listen 指令
    Nginx 配置
  • 原文地址:https://www.cnblogs.com/expedition/p/12207060.html
Copyright © 2020-2023  润新知