inline ll rd(){ ll x = 0; bool f = 0; char c = getchar(); for (; !isdigit(c); c = getchar()) f |= (c == '-'); for (; isdigit(c); c = getchar()) x = x * 10 + (c ^ 48); return f ? -x : x; }
#define N 200007 #define pb push_back
vector<int> e[N];
bool vis[N];
int deg[N];
queue<int> q;
int col[N], cnt;
voiddfs(int u, int c){ for (auto v : e[u]) if (!col[v]) { col[v] = c; dfs(v, c); } }
intmain(){ int n = rd(); for (int i = 1; i <= n; ++i) { int u = rd(), v = rd(); e[u].pb(v); e[v].pb(u); ++deg[u]; ++deg[v]; } for (int i = 1; i <= n; ++i) if (deg[i] == 1) {vis[i] = true; q.push(i);} while (!q.empty()) { int u = q.front(); q.pop(); for (auto v : e[u]) if (!vis[v]) { --deg[v]; if (deg[v] == 1) { vis[v] = true; q.push(v); } } } for (int i = 1; i <= n; ++i) if (!vis[i]) col[i] = ++cnt; for (int i = 1; i <= n; ++i) if (!vis[i]) dfs(i, col[i]); for (int q = rd(); q; --q) { int u = rd(), v = rd(); puts(col[u] == col[v] ? "Yes" : "No"); } return0; }
G. Yet Another RGB Sequence
计数 \(R\) 个 r ,\(G\) 个 g ,\(B\) 个 b
的字符串,且其中rg 子串恰好 \(k\
(k\le \min(R,G))\) 个。
先数出来 \(k\) 个 rg
、\(G-k\) 个 g 、\(B\) 个 b 的字符串个数是 \(\frac{(G+B)!}{k!(G-k)!B!}\)
(多重集的排列)
再将剩下的 \(R-k\) 个 r
插进去,因为不能插在 g 前面,所以只能插在 rg
或 b 的前面(及最后)
inline ll rd(){ ll x = 0; bool f = 0; char c = getchar(); for (; !isdigit(c); c = getchar()) f |= (c == '-'); for (; isdigit(c); c = getchar()) x = x * 10 + (c ^ 48); return f ? -x : x; }
#define N 2000007
#define mod 998244353
int fac[N], ifac[N];
inlineintfpow(int x, int t){ int res = 1; for (; t; t >>= 1, x = 1ll * x * x % mod) if (t & 1) res = 1ll * res * x % mod; return res; }
inlinevoidinit(){ fac[0] = ifac[0] = 1; for (int i = 1; i < N; ++i) fac[i] = 1ll * fac[i - 1] * i % mod; ifac[N - 1] = fpow(fac[N - 1], mod - 2); for (int i = N - 2; i; --i) ifac[i] = 1ll * ifac[i + 1] * (i + 1) % mod; }
inlineintC(int n, int m){ if (n < m) return0; return1ll * fac[n] * ifac[m] % mod * ifac[n - m] % mod; }
intmain(){ init(); int r = rd(), g = rd(), b = rd(), k = rd(); r -= k; g -= k; int ans = 1ll * fac[g + b + k] * ifac[g] % mod * ifac[b] % mod * ifac[k] % mod; b += k; printf("%lld\n", 1ll * ans * C(r + b, r) % mod); return0; }
inline ll rd(){ ll x = 0; bool f = 0; char c = getchar(); for (; !isdigit(c); c = getchar()) f |= (c == '-'); for (; isdigit(c); c = getchar()) x = x * 10 + (c ^ 48); return f ? -x : x; }
inlinevoidupd(int x, int y, ll w){ for (int i = x; i <= X; i += lowbit(i)) for (int j = y; j <= Y; j += lowbit(j)) c[i][j] = max(c[i][j], w); }
inline ll qmax(int x, int y){ ll res = 0; for (int i = x; i; i -= lowbit(i)) for (int j = y; j; j -= lowbit(j)) res = max(res, c[i][j]); return res; }
intmain(){ int n = rd(), m = 0; for (int i = 1; i <= n; ++i) { int t = rd(), x = rd(), y = rd(), w = rd(); if (t - x - y < 0 || t + x - y < 0) continue; g[++m].y = y; g[m].w = w; g[m].a = t - x - y; A.pb(g[m].a); g[m].b = t + x - y; B.pb(g[m].b); } n = m; auto cmp = [&](node a, node b) { if (a.y != b.y) return a.y < b.y; if (a.a != b.a) return a.a < b.a; return a.b < b.b; }; sort(g + 1, g + 1 + n, cmp); sort(all(A)); A.erase(unique(all(A)), A.end()); X = A.size(); sort(all(B)); B.erase(unique(all(B)), B.end()); Y = B.size();
ll ans = 0; for (int i = 1; i <= n; ++i) { int a = lower_bound(all(A), g[i].a) - A.begin() + 1; int b = lower_bound(all(B), g[i].b) - B.begin() + 1; ll nw = qmax(a, b) + g[i].w; ans = max(ans, nw); upd(a, b, nw); } printf("%lld\n", ans); return0; }