约瑟夫问题
解法
基础递推式 f[0] = 1;
f[i] = (f[i-1] + m) % i; 输出时f[n]要加上1,因为推导过程是n个人在从0开始编号的情况下。
证明
略.....
#include <iostream>
#include <cstdio>
#include <cmath>
#include <queue>
#include <map>
#include <cstring>
#include <algorithm>
#define rint register int
#define ll long long
#define lson x<<1
#define rson x<<1|1
#define mid ((st[x].l + st[x].r) >> 1)
using namespace std;
template <typename xxx> inline void read(xxx &x)
{
int f = 1;x = 0;
char c = getchar();
for(; c < '0' || c > '9' ; c = getchar()) if(c=='-') f = -1;
for(;'0' <= c && c <= '9'; c = getchar()) x = (x << 3) + (x << 1) + (c ^ 48);
x *= f;
}
template <typename xxx> inline void print(xxx x)
{
if(x < 0) {
putchar('-');
x = -x;
}
if(x > 9) print(x/10);
putchar(x % 10 + '0');
}
const int inf = 0x7fffffff;
const int maxn = 1000100;
const int mod = 10007;
ll n,m;
ll pre,now;
int main()
{
int t;read(t);
while(t--) {
read(n);read(m);
now = 0;
for(register ll i = 2;i <= n; ++i) {
if(now + m < i){
ll x = (i - now) / m;
if(i + x < n) {
i += x;
now = (now + x * m);
}
else {
now = now + (n - i) * m;
i = n;
}
}
now = (now + m)%i;
}
print(now + 1);putchar('\n');
}
}
/*
56行存在的意义:第i层刚开始时,now为第i-1层时的值,进入if后i加上x为i+x,now加上x个m值更新到了第i+x-1层,但每层的任务是更新该层的值,没有本行
i进入下一层循环变成i+x+1,则第i+x层并没有更新
45行不能写等于
*/