设 $income=kg$ ,则必有 $kg \leq pn $ (答案上限就是 $pn$ ),故 $income = kg = g \lfloor \frac { p*n } { g } \rfloor $
code:
1 2 3 4 5 6 7 8 9 10 11
voidsolve(){ longlong n, k, g; cin >> n >> k >> g; longlong p = ((g + 1) >> 1) - 1; if (p * n >= k * g) { cout << k * g << endl; } else { cout << p * n / g * g << endl; }
voidsolve(){ int A, B, C; longlong k; cin >> A >> B >> C >> k; for (int mx = mn[A + 1], i = mn[A]; i < mx; i++) { int l = max(mn[C] - i, mn[B]); int r = min(mn[C + 1] - i, mn[B + 1]); if (l >= r) continue; if (k <= r - l) { cout << i << " + " << l + k - 1 << " = " << i + l + k - 1 << endl; return; } else k -= r - l; } cout << -1 << endl; return; }
constint N = 1e5 + 5; int n, m; longlong k; vector<int> v[N]; vector<int> vec[N]; int col[N], cnt_col; int _stack[N], _t, dfn[N], low[N], cnt, siz[N]; bool book[N];
inlinevoidtarjan(int x){ //强连通分量 dfn[x] = low[x] = ++cnt; _stack[++_t] = x; book[x] = true; for (auto ver: v[x]) { if (!dfn[ver]) { tarjan(ver); low[x] = min(low[x], low[ver]); } elseif (book[ver]) low[x] = min(low[x], dfn[ver]); } if (dfn[x] == low[x]) { ++cnt_col; int p; do { p = _stack[_t]; col[p] = cnt_col; ++siz[cnt_col]; book[p] = false; --_t; } while (p != x); } }
int flag[N], dis[N]; bool solved[N];
inlinevoiddfs(int x, int d, int des){ dis[x] = d; flag[x] = des; for (auto ver: vec[x]) { if (flag[ver] != des) dfs(ver, d + 1, des); } }
int num[N];
int tag[N];
inlinebooldraw_col(int x, int now, int base_num, int des){ //尝试染色 num[x] = now; tag[x] = des; bool Flag = true; for (auto ver: vec[x]) { if (!Flag) returnfalse; if (tag[ver] != des) Flag &= draw_col(ver, (now + 1) % base_num, base_num, des); else Flag &= (num[ver] == ((num[x] + 1) % base_num)); } return Flag; }
int cnt_num[N];
inlinevoidDraw_col(int x, int now, int base_num, int des){ //染色,统计数目 num[x] = now; tag[x] = des; ++cnt_num[now]; for (auto ver: vec[x]) { if (tag[ver] != des) Draw_col(ver, (now + 1) % base_num, base_num, des); } }
intmain(){ cin >> n >> m >> k; for (int i = 1, x, y; i <= m; i++) { cin >> x >> y; v[x].push_back(y); } for (int i = 1; i <= n; i++) { if (!col[i]) tarjan(i); } for (int i = 1; i <= n; i++) { for (auto y: v[i]) { if (col[i] == col[y]) vec[i].push_back(y); } } int search_num = 0; longlong ans = 0; for (int i = 1; i <= n; i++) { if (solved[col[i]]) continue; solved[col[i]] = true; if (siz[col[i]] == 1) continue; int x = i, y = vec[x][0]; int d = 0; dfs(y, 0, y); d += dis[x] + 1; int g = 1; for (int j = 2; j * j <= d; j++) { if (d % j != 0) continue; int p = j, rem_num = 1; bool now_flag = true; while (d % p == 0) { ++search_num; if (now_flag && draw_col(x, 0, p, search_num)) rem_num = p; else now_flag = false; p *= j; } d /= (p / j); g *= rem_num; } if (d > 1 && (++search_num) && draw_col(x, 0, d, search_num)) g *= d; for (int j = 0; j < g; j++) cnt_num[j] = 0; ++search_num; Draw_col(x, 0, g, search_num); if (k % g == 0) { for (int j = 0; j < g; j++) ans += 1ll * cnt_num[j] * (cnt_num[j]+1) / 2; } elseif (g % 2 == 0 && k % g == g / 2) { for (int j = 0; j < g / 2; j++) ans += 1ll * cnt_num[j] * cnt_num[j + g / 2]; } } cout << ans << endl; }