题目:0,1,...,n-1这n个数字排成一个圆圈,从数字0开始每次从这个圆圈里面删除第m个数字。求这个圆圈里剩下的最后一个数字。
解法1:数组模拟
使用数组来模拟的话空间复杂度和时间复杂度都会比较高,不过为了锻炼下逻辑思维,我们先使用数组。将长度为n的数组初始化0,变量count表示当前退出的人数,只要count=n-1就可以完成任务。t表示报数计数,当t=m时就将数组当前i位置元素置1,表示i位置元素退出,遍历数组遇到元素为1的位置直接跳过。先处理要特殊处理的情况,然后再处理正常逻辑部分。
代码如下:
//n个人从0--n-1编号,从第一个人报数,数到m的退出.
int FindLastOne(int n,int m)
{
if(n<1 || m<1)
return -1;
int *data=new int[n];
memset(data,0,n*sizeof(int));
int t=0,count=0,i=0;
while(count<n-1)
{
if(data[i]==0)
t++;
if(t==m)
{
t=0;
data[i]=1;
++count;
}
i++;
if(i==n)
i=0;
}
int res;
for(i=0;i<n;i++)
if(data[i]==0)
res=i;
delete[] data;
return res;
}
解法2:数学魅力
int lastRemain(int n,int m)
{
if(n<1 || m<1)
return -1;
int last=0;
for(int i=2;i<=n;i++)
last=(last+m)%i;
return last;
}