1 条题解
-
0
自动搬运
来自洛谷,原作者为

Vocalise
「不入流的划水选手」搬运于
2025-08-24 22:09:38,当前版本为作者最后更新于2021-02-16 21:50:38,作者可能在搬运后再次修改,您可在原文处查看最新版自动搬运只会搬运当前题目点赞数最高的题解,您可前往洛谷题解查看更多
以下是正文
题意
求 以内模 值属于集合 且 模 值属于集合 的数的数量。
首先对一个模型作介绍。
对于 中的数都建立一个点,若点 连一条边至 ,那么整个图会分为 个独立的环,每个环的点数是 。
说明:
每一个点走若干个 步回到自己,同时经过了若干个 总长,因此经过的总长是 ,点数 。而总点数 ,所以环数 。
假设 。因为 中的数要不变地唯一对应到 中的一个数。
在这个图上考虑问题,我们可以枚举 ,在图上直接找到它,考虑它沿边走 步得到的数是 ,我们需要计算包括自己,在 以内,一共经过多少 。
要解决的问题直观了起来。我们可以在图上标记所有 权值为 其余为 ,预处理环上总和与 圈以内的前缀和。
对于 ,包括自己一共要统计 个点。首先直接计算整圈,然后对于留下的不满一圈的路径,分类讨论一下计算即可。
要注意的是:前缀和中选定的起点值是 还是总和; 要直接舍弃。
#include <cstdio> #include <iostream> #include <cstring> #include <cmath> #include <algorithm> typedef long long ll; const int N = 1000001; inline ll read() { ll x = 0, f = 1; char ch = getchar(); while(ch > '9' || ch < '0') { if(ch == '-') f = -1; ch = getchar(); } do x = x * 10 + ch - 48, ch = getchar(); while(ch >= '0' && ch <= '9'); return x * f; } int gcd(int x,int y) { return !y ? x : gcd(y,x % y); } int P,Q,n,m,a[N],b[N]; ll t; int vis[N],at[N]; ll dist[N],ring[N],sum[N],len; ll Prefix(ll a,ll x) { if(!x) return 0; ll b = (a + (x - 1) * P) % Q; if(x + dist[a] > len) return sum[a] - (ring[a] - ring[b] - at[a]); else return ring[b] - ring[a] + at[a]; } ll Calc(ll T) { ll ans = 0; for(int i = 1;i <= n;i++) { if(T < a[i]) continue; ll st = (T - a[i]) / P + 1; ans += st / len * sum[a[i]] + Prefix(a[i],st % len); } return ans; } int main() { P = read(), Q = read(), n = read(), m = read(), t = read(); if(P > Q) { std::swap(P,Q), std::swap(n,m); for(int i = 1;i <= m;i++) b[i] = read(); for(int i = 1;i <= n;i++) a[i] = read(); } else { for(int i = 1;i <= n;i++) a[i] = read(); for(int i = 1;i <= m;i++) b[i] = read(); } for(int i = 1;i <= m;i++) at[b[i]] = true; for(int i = 0;i < Q;i++) if(!vis[i]) { int p = i, k = (i + P) % Q; while(!vis[p]) { vis[p] = true, dist[k] = dist[p] + 1; ring[k] = ring[p] + at[k]; p = k, k = (k + P) % Q; } k = (i + P) % Q, sum[i] = ring[i], ring[i] = dist[i] = 0; while(k != i) sum[k] = sum[i], k = (k + P) % Q; } len = Q / gcd(P,Q); std::printf("%lld\n",Calc(t - 1)); return 0; }
- 1
信息
- ID
- 4319
- 时间
- 2000ms
- 内存
- 256MiB
- 难度
- 6
- 标签
- 递交数
- 0
- 已通过
- 0
- 上传者