原题面中:
操作一,在集合 S 中加入一个新元素,其代号为 X,保证 X 在当前集合中不存在。
经过 assert 发现民间数据 #11 存在重复添加元素的情况。
同时我的代码一开始只用 vis 判了一个数是否存在民间数据全 WA 了,但用 cnt 判断一个数是否被消完了就 AC 了。
所以可能其他民间数据也有点问题。
这个是代码:
// URL: https://www.luogu.com.cn/problem/P9809
// Memory Limit: 256 MB
// Time Limit: 1000 ms
//
// Powered by CP Editor (https://cpeditor.org)
#include<bits/stdc++.h>
const int nn = 3e5 + 1;
const int maxn = 3e5 + 10, maxm = 600;
int nr[maxm];
// bool vis[maxn];
int cnt[maxn];
struct opt {
int o, x, id;
};
opt q[maxn];
int ans[maxn];
int fa[maxn];
int getfa(int x) {
return fa[x] == x ? x : (fa[x] = getfa(fa[x]));
}
int main() {
int n;
scanf("%d", &n);
memset(nr, 0x3f, sizeof(nr));
int m = 0;
for (int i = 1; i <= n; i++) {
char s[5];
int x;
scanf("%s%d", s, &x);
q[i] = {s[0] == 'A', x, 0};
if (q[i].o) {
cnt[x]++;
// vis[x] = 1;
for (int i = 1; i < maxm; i++) {
nr[i] = std::min(nr[i], x % i);
}
} else {
q[i].id = ++m;
if (x < maxm) {
ans[m] = nr[x];
}
}
}
int now = nn;
for (int i = nn; ~ i; i--) {
if (cnt[i]) {
now = i;
}
// if (vis[i]) {
// now = i;
// }
fa[i] = now;
}
for (int i = n; i >= 1; i--) {
if (q[i].o) {
if (! (--cnt[q[i].x])) {
fa[q[i].x] = q[i].x + 1;
}
// fa[q[i].x] = q[i].x + 1;
} else {
if (q[i].x >= maxm) {
ans[q[i].id] = nn;
for (int j = 0; j <= 3e5; j += q[i].x) {
if (getfa(j) != nn) {
ans[q[i].id] = std::min(ans[q[i].id], getfa(j) - j);
}
}
}
}
}
for (int i = 1; i <= m; i++) {
printf("%d\n", ans[i]);
}
return 0;
}