约瑟夫问题的数学解法

问题描述:n个人(编号0~(n-1)),从0开始报数,报到(m-1)的退出,剩下的人继续从0开始报数。求胜利者的编号。

第一轮:

编号: 0, 1, 2, ...m-2,m-1,m,m+1.... n-1

在报数之后,m-1 退出

编号: 0,1,2,.....m-2,m,m+1,....n-1


第二轮(人未退出):

轮到 m 开始报数,此时报数序列如下:

(式1)编号:m,m+1,....0,1,2...n-1.....m-2

对这个序列重新编号

(式2)编号:0,1,2.....n-2

由式2的编号x 计算 式1的编号 x‘ 可用此公式:

x = (x' + m)% N   N 为当前环中人数加1

ps:我不知道这个公式如何得出的


也就是说,如果已知 第i轮某个人的编号为x,则可以计算出 第i-1轮他的编号,此处的编号为每一轮的编号都是从 0-n-1 重新编号过的编号(下)。

可见第n轮只剩下一个人的编号为 0 此人即为胜利者

那么 第n-1轮 胜利者的编号为 (0+m)%2

以此类推可的 第一轮胜利者的编号,即原始编号

代码如下:

#include <stdio.h>
int main(void)  
{  
    int i,s = 0;
    int m = 3;
    int n = 20;
    for(i=2; i<=n; i++){
        s = (s+m)%i;
    }
    printf("%d\n", s);
    return 0;  
} 


 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值