牛客题解 约瑟夫环
链接:https://ac.nowcoder.com/acm/problem/22227
来源:牛客网
题解
作者 岛田小雅
正统的约瑟夫环我不会,看了一眼范围直接开始乱搞了。
我选择的方法是模拟,用递归函数实现(虽然也可以不用)。
设置一个递归函数 \(\operatorname{operate}()\),两个参数分别存正在报数的人 \(x\) 和他要报的数字 \(num\)。因为有人要出队,所以再开个 \(vis\) 数组存第 \(i\) 个人还在不在队伍里。函数要一直递归到只剩下一个人,所以再用一个变量 \(r\) 存还剩下几个人。每次一个人出队就维护 \(r\),当 \(r=1\) 的时候,结束递归。
最后在所有 \(vis\) 里面找那个还在队伍里的人然后输出出来就好了。
我会承认写的时候样例测了好几次都没过是因为少了个 return 吗。
话说回来为什么这么像 DFS 呢……
AC 代码
作者 岛田小雅
#include <bits/stdc++.h>
using namespace std;
const int N = 1e2+2;
int n, k, m;
bool vis[N];
int r;
void operate(int x, int num)
{
x %= n;
if(r == 1) return;
if(vis[x])
{
operate(x+1,num);
return;
}
if(num == m)
{
vis[x] = true;
r--;
operate(x+1,1);
}
else operate(x+1,num+1);
}
int main()
{
ios::sync_with_stdio(0); cin.tie(0); cout.tie(0);
cin >> n >> k >> m;
r = n;
for(int i = 0; i < n; i++) vis[i] = false;
operate(k,1);
for(int i = 0; i < n; i++)
{
if(!vis[i])
{
cout << i;
break;
}
}
return 0;
}