NYOJ 361 又遇约瑟夫环 (打表)

描述
假设有2k个人围着一个圆桌坐着,前k个是好人,后k个是坏人 。现在开始,每m个人踢掉一个,比如有6个人,m=5,那么,被踢掉的人依次是5,4,6,2,3,1。现在要求,在踢掉第一个好人前,必需把所有的坏人踢掉,问,给定一个k,求满足这个要求的最小的m,现在希望你写一个程序,快速的帮助小珂,计算出来这个m。

输入
每行一个整数k(k<15),0表示输入结束.总测试数据的组数不多于200.
输出
各个组对应的最小的m,换行结束。
样例输入
3
4
0
样例输出
5
30

与基本约瑟夫环不同的是,本题要求前k个好人不能被踢掉,就可以认为前0-k-1个编号不会改变(不会有空位),所以可以直接求出每一次删掉的人的编号是否小于k,又因为k的值较小,所以直接打表,输出结果。

还可以直接将表给出来,如果追求0ms通过的话。

#include <cstdio>
int main()
{
    int k;
    int ans[28]={0};
    int Joseph[14]={0};
    while(scanf("%d",&k)&&k!=0)
    {
        if(Joseph[k]!=0)
        {
            printf("%d\n",Joseph[k]);
            continue;
        }
        int n=2*k;
        int m=k+1;
        for(int i=1;i<=k;i++)
        {
            ans[i]=(ans[i-1]+m-1)%(n-i+1);
            if(ans[i]<k)
            {
                m++;
                i=0;
            }
        }
        Joseph[k]=m;
        printf("%d\n",Joseph[k]);
    }
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值