C语言实例-约瑟夫生者死者小游戏

问题:

30个人在一条船上,超载,需要15人下船。于是人们排成一队,排队的位置即为他们的编号。报数,从1开始,数到9的人下船,如此循环,直到船上仅剩15人为止,问都有哪些编号的人下船了呢?

代码:
#include <stdio.h>

int main(){

    int count = 0; //下船人数
    int baoshu = 0;//报数
    int i=0;//编号
    int b[31] = {0};

    //当下船人数小于15时,一直循环
    while(count<15){
        
        //从1到30循环
        i++;
        if(i >= 31) i=1;
        
        //报数时跳过已经标记为下船的人
        if(b[i] == 0){baoshu++;}

        if(baoshu == 9) 
        {
            b[i] = 1; //标记为下船
            count++;//下船人数
            printf("i=%d \tb[%d]=%d\t 第%d个下船\t 编号:%d\n",i,i,b[i],count,i);

            //重置报数 
            //报数归1,同时i值增加至下一个b[i]!=1的位置
            //do-while循环是解决连续多个b[i]=1的情况
            do{
                i++;
                if(i >= 31) i=1;
            } while (b[i]!=0);
            baoshu = 1;
        }
    }

    return 0;
}
运行结果:

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
好的,这是一个经典的问题,可以用循环链表来解决。下面是使用C语言编写的解决方案: ```c #include <stdio.h> #include <stdlib.h> typedef struct node { int num; struct node *next; } Node; // 创建循环链表,返回头结点指针 Node *createList(int n) { Node *head = (Node *)malloc(sizeof(Node)); Node *tail = head; head->num = 1; for (int i = 2; i <= n; i++) { Node *p = (Node *)malloc(sizeof(Node)); p->num = i; tail->next = p; tail = p; } tail->next = head; return head; } // 释放链表内存 void freeList(Node *head) { Node *p = head->next; while (p != head) { Node *temp = p; p = p->next; free(temp); } free(head); } // 模拟过程,返回下船的人的编号 int *josephus(int n, int m, int k) { Node *head = createList(n); Node *tail = head; while (tail->next != head) { tail = tail->next; } int *res = (int *)malloc(k * sizeof(int)); int count = 0; while (tail != head) { for (int i = 1; i < m; i++) { tail = head; head = head->next; } res[count++] = head->num; tail->next = head->next; Node *temp = head; head = head->next; free(temp); } res[count++] = head->num; // 只输出最后下船的15个人的编号 int *result = (int *)malloc(k * sizeof(int)); for (int i = 0; i < k; i++) { result[i] = res[i + n - k]; } freeList(head); free(res); return result; } int main() { int n = 30; // 总人数 int m = 9; // 报到9的人下船 int k = 15; // 最后只剩15人 int *res = josephus(n, m, k); printf("下船的人的编号为:"); for (int i = 0; i < k; i++) { printf("%d ", res[i]); } printf("\n"); free(res); return 0; } ``` 上面的代码中,我们先创建了一个循环链表,然后模拟过程,每次从链表中删除第m个节点,直到只剩下15个节点为止,最后输出下船的人的编号。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值