結果
問題 | No.1197 モンスターショー |
ユーザー |
![]() |
提出日時 | 2023-02-01 20:53:24 |
言語 | C++17 (gcc 13.3.0 + boost 1.87.0) |
結果 |
AC
|
実行時間 | 639 ms / 3,000 ms |
コード長 | 8,060 bytes |
コンパイル時間 | 2,021 ms |
コンパイル使用メモリ | 152,424 KB |
最終ジャッジ日時 | 2025-02-10 08:05:17 |
ジャッジサーバーID (参考情報) |
judge1 / judge2 |
(要ログイン)
ファイルパターン | 結果 |
---|---|
sample | AC * 2 |
other | AC * 41 |
コンパイルメッセージ
In member function ‘void Centroid_Decomposition::add(int, int)’, inlined from ‘void solve()’ at main.cpp:376:17: main.cpp:331:43: warning: ‘id’ may be used uninitialized [-Wmaybe-uninitialized] 331 | nums[g][id] += a; | ^ main.cpp: In function ‘void solve()’: main.cpp:322:32: note: ‘id’ was declared here 322 | int g = c; int id; | ^~ In member function ‘ll Centroid_Decomposition::query(int)’, inlined from ‘void solve()’ at main.cpp:385:21: main.cpp:351:62: warning: ‘id’ may be used uninitialized [-Wmaybe-uninitialized] 351 | res += pdist[g] - dists[g][id]; | ^ main.cpp: In function ‘void solve()’: main.cpp:340:32: note: ‘id’ was declared here 340 | int g = c; int id; | ^~ In member function ‘void Centroid_Decomposition::add(int, int)’, inlined from ‘void solve()’ at main.cpp:381:10: main.cpp:331:43: warning: ‘id’ may be used uninitialized [-Wmaybe-uninitialized] 331 | nums[g][id] += a; | ^ main.cpp: In function ‘void solve()’: main.cpp:322:32: note: ‘id’ was declared here 322 | int g = c; int id; | ^~ In member function ‘void Centroid_Decomposition::add(int, int)’, inlined from ‘void solve()’ at main.cpp:381:38: main.cpp:331:43: warning: ‘id’ may be used uninitialized [-Wmaybe-uninitialized] 331 | nums[g][id] += a; | ^ main.cpp: In function ‘void solve()’: main.cpp:322:32: note: ‘id’ was declared here 322 | int g = c; int id; |
ソースコード
#include<iostream>#include<string>#include<cstdio>#include<vector>#include<cmath>#include<algorithm>#include<functional>#include<iomanip>#include<queue>#include<ciso646>#include<random>#include<map>#include<set>#include<bitset>#include<stack>#include<unordered_map>#include<utility>#include<cassert>#include<complex>#include<numeric>#include<array>using namespace std;//#define int long longtypedef long long ll;typedef unsigned long long ul;typedef unsigned int ui;constexpr ll mod = 998244353;const ll INF = mod * mod;typedef pair<int, int>P;#define stop char nyaa;cin>>nyaa;#define rep(i,n) for(int i=0;i<n;i++)#define per(i,n) for(int i=n-1;i>=0;i--)#define Rep(i,sta,n) for(int i=sta;i<n;i++)#define rep1(i,n) for(int i=1;i<=n;i++)#define per1(i,n) for(int i=n;i>=1;i--)#define Rep1(i,sta,n) for(int i=sta;i<=n;i++)#define all(v) (v).begin(),(v).end()typedef pair<ll, ll> LP;typedef double ld;typedef pair<ld, ld> LDP;const ld eps = 1e-12;const ld pi = acosl(-1.0);ll mod_pow(ll x, ll n, ll m) {ll res = 1;while (n) {if (n & 1)res = res * x % m;x = x * x % m; n >>= 1;}return res;}struct modint {ll n;modint() :n(0) { ; }modint(ll m) :n(m) {if (n >= mod)n %= mod;else if (n < 0)n = (n % mod + mod) % mod;}operator int() { return n; }};bool operator==(modint a, modint b) { return a.n == b.n; }modint operator+=(modint& a, modint b) { a.n += b.n; if (a.n >= mod)a.n -= mod; return a; }modint operator-=(modint& a, modint b) { a.n -= b.n; if (a.n < 0)a.n += mod; return a; }modint operator*=(modint& a, modint b) { a.n = ((ll)a.n * b.n) % mod; return a; }modint operator+(modint a, modint b) { return a += b; }modint operator-(modint a, modint b) { return a -= b; }modint operator*(modint a, modint b) { return a *= b; }modint operator^(modint a, ll n) {if (n == 0)return modint(1);modint res = (a * a) ^ (n / 2);if (n % 2)res = res * a;return res;}ll inv(ll a, ll p) {return (a == 1 ? 1 : (1 - p * inv(p % a, a)) / a + p);}modint operator/(modint a, modint b) { return a * modint(inv(b, mod)); }const int max_n = 1 << 20;modint fact[max_n], factinv[max_n];void init_f() {fact[0] = modint(1);for (int i = 0; i < max_n - 1; i++) {fact[i + 1] = fact[i] * modint(i + 1);}factinv[max_n - 1] = modint(1) / fact[max_n - 1];for (int i = max_n - 2; i >= 0; i--) {factinv[i] = factinv[i + 1] * modint(i + 1);}}modint comb(int a, int b) {if (a < 0 || b < 0 || a < b)return 0;return fact[a] * factinv[b] * factinv[a - b];}ul gcd(ul a, ul b) {if (a < b)swap(a, b);while (b) {ul r = a % b; a = b; b = r;}return a;}struct lcagraph {private:int n;vector<vector<int>> G;vector<vector<int>> parent;vector<int> depth;int root;int tmp;public:lcagraph(int n_) {n = n_;G.resize(n);parent.resize(n);depth.resize(n);tmp = 0;int cop = n;while (cop) {tmp++; cop /= 2;}rep(i, n)parent[i].resize(tmp);root = 0;}lcagraph() {}void init(int n_) {n = n_;G.resize(n);parent.resize(n);depth.resize(n);tmp = 0;int cop = n;while (cop) {tmp++; cop /= 2;}rep(i, n)parent[i].resize(tmp);root = 0;}void add_edge(int a, int b) {G[a].push_back(b);G[b].push_back(a);}void dfs(int id, int fr, int d) {parent[id][0] = fr;depth[id] = d;rep(j, G[id].size()) {int to = G[id][j];if (to == fr)continue;dfs(to, id, d + 1);}}void complete(int r = 0) {root = r;dfs(root, -1, 0);rep(j, tmp - 1)rep(i, n) {if (parent[i][j] < 0)parent[i][j + 1] = -1;else parent[i][j + 1] = parent[parent[i][j]][j];}}int lca(int u, int v) {if (depth[u] > depth[v])swap(u, v);for (int k = 0; k < tmp; k++) {if ((depth[v] - depth[u]) >> k & 1) {v = parent[v][k];}}if (u == v)return u;for (int k = tmp - 1; k >= 0; k--) {if (parent[u][k] != parent[v][k]) {u = parent[u][k];v = parent[v][k];}}return parent[u][0];}int dep(int x) {return depth[x];}int dist(int x, int y) {int l = lca(x, y);return depth[x] + depth[y] - 2 * depth[l];}int find_par(int x, int d) {rep(i, tmp)if (d & (1 << i))x = parent[x][i];return x;}};struct edge {int to;};struct Centroid_Decomposition {private:int n;vector<vector<edge>> G;vector<vector<int>> fG; int root;vector<int> par, parid;vector<vector<int>> pardists;vector<vector<ll>> dists;vector<vector<int>> nums;vector<ll> pdist;vector<int> pnum;lcagraph lg;public:Centroid_Decomposition(int n_) {n = n_;G.resize(n);par.resize(n);parid.resize(n);pardists.resize(n);fG.resize(n); root = -1;dists.resize(n);nums.resize(n);pdist.resize(n);pnum.resize(n);}void add_edge(int a, int b) {G[a].push_back({ b });G[b].push_back({ a });}void complete() {vector<int> exi(n, 0);vector<int> ori(n); rep(i, n)ori[i] = i;int tmp = 0;function<int(int, int, int&, int&)> szdfs = [&](int id, int fr, int& g, int& sz)->int {int res = 1;int ma = 0;for (edge e : G[id]) {if (tmp != exi[e.to])continue;if (e.to == fr)continue;int nex = szdfs(e.to, id, g, sz);ma = max(ma, nex);res += nex;}if (ma <= sz / 2 && sz - res <= sz / 2)g = id;return res;};function<int(vector<int>)> cdfs = [&](vector<int> v)->int {tmp++;if (v.empty())return 0;for (int id : v) {exi[id]++;}int g;int sz = v.size();szdfs(v[0], -1, g, sz);pnum[g] = 0;pardists[g].push_back(0);for (edge e : G[g]) {if (!exi[e.to])continue;if (exi[e.to] != tmp)continue;int tm = dists[g].size();dists[g].push_back(0);nums[g].push_back(0);queue<P> vs;vs.push({ e.to,g });int d = 0;vector<int> nex;while (!vs.empty()) {d++;int len = vs.size();rep(aa, len) {P p = vs.front(); vs.pop();int v = p.first, fr = p.second;pardists[v].push_back(d);nex.push_back(v);for (edge e : G[v]) {if (e.to == fr)continue;if (tmp != exi[e.to])continue;vs.push({ e.to,v });}}}int ng = cdfs(nex);fG[g].push_back(ng);par[ng] = g;parid[ng] = tm;}for (int id : v) {exi[id]--;}tmp--;return g;};root = cdfs(ori); par[root] = -1;rep(i, n)reverse(all(pardists[i]));//lcalg.init(n);rep(i, n) {for (edge e : G[i]) {if (i < e.to) {lg.add_edge(i, e.to);}}}lg.complete();}void add(int c, int a) {int g = c; int id;for(int i=0;g>=0;i++){if (g == c) {pnum[g] += a;}else {//d(g,c)int dist = pardists[c][i];pnum[g] += a;nums[g][id] += a;pdist[g] += a * dist;dists[g][id] += a * dist;}id = parid[g];g = par[g];}}ll query(int c) {int g = c; int id;ll res = 0;for(int i=0;g>=0;i++){if (g == c) {res += pdist[g];}else {//d(g,c)ll dist = pardists[c][i];//cout << res << "\n";res += pdist[g] - dists[g][id];//cout << res << "\n";//cout << pnum[g] << "wow" << nums[g][id] << "\n";res += (pnum[g] - nums[g][id]) * dist;//cout << "? " << g << " " << c << " " << dist << " " << res << "\n";}id = parid[g];g = par[g];}return res;}};void solve() {int n, k, q; cin >> n >> k >> q;vector<int> c(k); rep(i, k) {cin >> c[i]; c[i]--;}Centroid_Decomposition cd(n);rep(i, n - 1) {int a, b; cin >> a >> b; a--; b--;cd.add_edge(a, b);}cd.complete();rep(i, k)cd.add(c[i], 1);rep(i, q) {int t; cin >> t;if (t == 1) {int p, d; cin >> p >> d; p--; d--;cd.add(c[p], -1); c[p] = d; cd.add(c[p], 1);}else {int p; cin >> p; p--;ll ans = cd.query(p);cout << ans << "\n";}}}signed main() {ios::sync_with_stdio(false);cin.tie(0);cout << fixed << setprecision(10);init_f();//expr();//int t; cin >> t; rep(i, t)//while (cin >> n >> m>>s1>>s2>>t, n)solve();return 0;}