結果
問題 | No.529 帰省ラッシュ |
ユーザー | tonegawa |
提出日時 | 2020-05-12 17:28:47 |
言語 | C++14 (gcc 12.3.0 + boost 1.83.0) |
結果 |
AC
|
実行時間 | 2,374 ms / 4,500 ms |
コード長 | 5,809 bytes |
コンパイル時間 | 2,155 ms |
コンパイル使用メモリ | 137,336 KB |
実行使用メモリ | 122,908 KB |
最終ジャッジ日時 | 2024-09-13 15:50:43 |
合計ジャッジ時間 | 20,078 ms |
ジャッジサーバーID (参考情報) |
judge3 / judge2 |
(要ログイン)
テストケース
テストケース表示入力 | 結果 | 実行時間 実行使用メモリ |
---|---|---|
testcase_00 | AC | 102 ms
82,688 KB |
testcase_01 | AC | 102 ms
82,688 KB |
testcase_02 | AC | 104 ms
82,688 KB |
testcase_03 | AC | 103 ms
82,688 KB |
testcase_04 | AC | 120 ms
83,200 KB |
testcase_05 | AC | 121 ms
83,024 KB |
testcase_06 | AC | 122 ms
83,072 KB |
testcase_07 | AC | 122 ms
82,944 KB |
testcase_08 | AC | 1,142 ms
120,140 KB |
testcase_09 | AC | 1,009 ms
116,612 KB |
testcase_10 | AC | 1,234 ms
111,748 KB |
testcase_11 | AC | 1,289 ms
111,576 KB |
testcase_12 | AC | 683 ms
113,968 KB |
testcase_13 | AC | 564 ms
122,164 KB |
testcase_14 | AC | 1,048 ms
122,908 KB |
testcase_15 | AC | 2,329 ms
110,980 KB |
testcase_16 | AC | 2,374 ms
110,988 KB |
testcase_17 | AC | 1,142 ms
119,888 KB |
testcase_18 | AC | 1,108 ms
120,096 KB |
testcase_19 | AC | 1,137 ms
117,592 KB |
ソースコード
#include <iostream> #include <string> #include <vector> #include <queue> #include <deque> #include <algorithm> #include <set> #include <map> #include <bitset> #include <cmath> #include <functional> #include <iomanip> #define vll vector<ll> #define vvvl vector<vvl> #define vvl vector<vector<ll>> #define VV(a, b, c, d) vector<vector<d> >(a, vector<d>(b, c)) #define VVV(a, b, c, d) vector<vvl>(a, vvl(b, vll (c, d))); #define re(c, b) for(ll c=0;c<b;c++) #define all(obj) (obj).begin(), (obj).end() typedef long long int ll; typedef long double ld; using namespace std; //二重辺連結成分分解 struct Graph{ int MAX_V; vector<set<ll>> G; vector<set<ll>> rG; vector<bool> used; vector<int> cmp; vector<int> vs; Graph(ll V){ MAX_V = V; G = vector<set<ll>>(MAX_V+1); rG = vector<set<ll>>(MAX_V+1); used.resize(MAX_V+1, false); cmp.resize(MAX_V+1, 0); } void add_edge(int from, int to){ G[from].insert(to); G[to].insert(from); rG[from].insert(to); rG[to].insert(from); } void dfs(int v){ used[v] = true; for(auto to:G[v]) { ll a = v, b = to; G[b].erase(a); rG[a].erase(b); if(!used[to]) dfs(to); } vs.push_back(v); } void rdfs(int v, int k){ used[v] = true; cmp[v] = k; for(auto to:rG[v]) { if(!used[to]) rdfs(to, k); } } int scc(int V){ for(int i=0;i<MAX_V;i++) used[i] = false; vs.clear(); for(int i=0;i<MAX_V;i++) if(!used[i]) dfs(i); for(int i=0;i<MAX_V;i++) used[i] = false; int k = 0; for(int i=vs.size()-1;i>=0;i--) if(!used[vs[i]]) rdfs(vs[i], k++); return k; } //変換後の頂点->辺群 vvl build(ll n){ vvl ret = VV(MAX_V+1, 0, 0, ll); vector<set<ll>> T(MAX_V+1); scc(n); for(int i=0;i<=n;i++){ for(auto to:G[i]){ T[cmp[i]].insert(cmp[to]); T[cmp[to]].insert(cmp[i]); } } for(int i=0;i<=n;i++){ for(auto to:T[i]){ ret[i].push_back(to); } } return ret; } }; template< typename G > struct HeavyLightDecomposition { G &g; vector< int > sz, in, out, head, rev, par; HeavyLightDecomposition(G &g) : g(g), sz(400000), in(400000), out(400000), head(400000), rev(400000), par(400000) {} void dfs_sz(int idx, int p) { par[idx] = p; sz[idx] = 1; if(g[idx].size() && g[idx][0] == p) swap(g[idx][0], g[idx].back()); for(auto &to : g[idx]) { if(to == p) continue; dfs_sz(to, idx); sz[idx] += sz[to]; if(sz[g[idx][0]] < sz[to]) swap(g[idx][0], to); } } void dfs_hld(int idx, int par, int ×) { in[idx] = times++; rev[in[idx]] = idx; for(auto &to : g[idx]) { if(to == par) continue; head[to] = (g[idx][0] == to ? head[idx] : to); dfs_hld(to, idx, times); } out[idx] = times; } void build() { dfs_sz(0, -1); int t = 0; dfs_hld(0, -1, t); } int la(int v, int k) { while(1) { int u = head[v]; if(in[v] - k >= in[u]) return rev[in[v] - k]; k -= in[v] - in[u] + 1; v = par[u]; } } int lca(int u, int v) { for(;; v = par[head[v]]) { if(in[u] > in[v]) swap(u, v); if(head[u] == head[v]) return u; } } template< typename T, typename Q, typename F > T query(int u, int v, const T &ti, const Q &q, const F &f, bool edge = false) { T l = ti, r = ti; for(;; v = par[head[v]]) { if(in[u] > in[v]) swap(u, v), swap(l, r); if(head[u] == head[v]) break; l = f(q(in[head[v]], in[v] + 1), l); } return f(f(q(in[u] + edge, in[v] + 1), l), r); // return {f(q(in[u] + edge, in[v] + 1), l), r}; } template< typename Q > void add(int u, int v, const Q &q, bool edge = false) { for(;; v = par[head[v]]) { if(in[u] > in[v]) swap(u, v); if(head[u] == head[v]) break; q(in[head[v]], in[v] + 1); } q(in[u] + edge, in[v] + 1); } }; //------------------------------------------------------------------- //------------------------------------------------------------------- struct segtree{ ll M=1, INF = 1000000000000000000, INIT; vector<vll> dat; segtree(ll N, ll num){ INIT = num; while(M<N) M*=2; dat.resize(M*2-1, vll{num, -1}); } void update(vll x, ll k, ll l=0, ll r=-1){ if(r==-1) r = M; k+=M-1; dat[k] = x; while(k>0) { k = (k-1)/2; dat[k] = max(dat[k*2+1], dat[k*2+2]); } } vll query(ll a, ll b=-1, ll k=0, ll l=0, ll r=-1){ if(r==-1) r = M; if(b==-1) b = M; if(r<=a || b<=l) return vll{INIT, -INIT}; if(a<=l && r<=b) return dat[k]; vll A = query(a, b, k*2+1, l, (l+r)/2); vll B = query(a, b, k*2+2, (l+r)/2, r); return max(A, B); } }; //------------------------------------------------------------------- #include <queue> int main(int argc, char const *argv[]) { ll a, b, c, n, m, q;std::cin >> n >> m >> q; Graph scc(n+1); re(i, m){ scanf("%lld %lld", &a, &b); scc.add_edge(a, b); } vvl G = scc.build(n); HeavyLightDecomposition<vvl> hld(G); hld.build(); segtree seg(300000, -1); vector<priority_queue<ll>> max_cost(400000); re(i, q){ scanf("%lld %lld %lld", &a, &b, &c); if(a==1){ b = scc.cmp[b]; max_cost[b].push(c); ll MAX = max_cost[b].top(); hld.add(b, b, [&](ll x, ll y){seg.update(vll{MAX, b}, x);}); }else{ b = scc.cmp[b]; c = scc.cmp[c]; vll q = hld.query(b, c, vll{-1, -1}, [&](ll x, ll y){return seg.query(x, y);}, [&](vll x, vll y){return max(x, y);} ); printf("%lld\n", q[0]); if(q[0]!=-1) { max_cost[q[1]].pop(); ll MAX = (!max_cost[q[1]].empty()?max_cost[q[1]].top():-1); hld.add(q[1], q[1], [&](ll x, ll y){seg.update(vll{MAX, q[1]}, x);}); } } } return 0; }