约瑟夫环问题解法

约瑟夫环问题是类似这样的问题:

给你一个序列,编号为1到n,给你一个数m让你从第一个人开始数,数到m就删除这个数。就是这样的问题,一般是问最后一个删除的是哪个。

我了解到得解法有两种:

第一:暴力循环枚举:

时间复杂度是O(n^2)的。

代码:简单模拟,就不上了......................(你咬我)算了,我就不贴了,毕竟这么简单,这都不行那还是用后面个吧

第二:公式推导得到:

时间复杂度O(n)的。(很优秀了)

代码:

int Joseph(int n , int m )
{
    int num = 0 ;
    for(int i = 2 ; i <= n ; i ++) num = (num + m) % i ;
    return num + 1 ;///返回最后删除的那个数
}

就是这样.........

推导过程是:(很重要,不能知其然,不知其所以然)

以问题的形式得出:

N个人(编号0~(N-1)),从0开始报数,报到(M-1)的删掉,剩下的数继续从0开始报数。求最后删掉的编号。

N个人编号如下:

0 , 1 ............ m-2 , m-1,m,..............n-2,n-1,n
第一个删掉的数是(M-1)%N,报到3的数删掉,则第一个删掉的数的编号是(3-1)%41=2。编号(M-1)%N删掉后,剩下的数排列如下:

0 , 1............m-2,     ,m,...............n-2,n-1

有数删掉后,下一个位置M又从零开始报数,因此环应该如下:
m,m+1,........n-1,0,1.................m-2

将上面的排列顺序重新编号:

m,m+1,........n-1,0,1.................m-3,m-2

0,1,..............m-2,m-1,m...........n-1,n

 

问题变为(N-1)个人,报到为(M-1)的人自杀,问题规模减小了。这样一直进行下去,最后剩下编号为0的人。用函数表示:

F(1)=0

当有2个人的时候(N=2),报道(M-1)的人自杀,最后自杀的人是谁?应该是在只有一个人时,报数时得到的最后自杀的序号加上M,因为报到M-1的人已经自杀,只剩下2个人,另一个自杀者就是最后自杀者,用函数表示:

F(2)=F(1)+M

可以得到递推公式:

F(i)=F(i-1)+M

因为可能会超出总人数范围,所以要求模

F(i)=(F(i-1)+M)%i

所以就可以O(n)的求出来了

菜得不一样,菜出新高度!

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值