Submission #1188948

#TimeUsernameProblemLanguageResultExecution timeMemory
1188948alexddCollapse (JOI18_collapse)C++20
0 / 100
39 ms14016 KiB
#include "collapse.h" #include<bits/stdc++.h> using namespace std; int n; struct DSU { int father[100005],siz[100005]; vector<pair<pair<int,int>,int>> history; void init() { history.clear(); for(int i=0;i<n;i++) father[i]=i, siz[i]=1; } int gas(int x) { if(father[x]!=x) return gas(father[x]); return x; } void unite(int x, int y) { x = gas(x); y = gas(y); if(x==y) return; history.push_back({{y,father[y]},0}); history.push_back({{x,siz[x]},1}); father[y] = x; siz[x] += siz[y]; } int get_time() { return history.size(); } void rollback(int t) { while((int)history.size() > t) { if(history.back().second == 0) father[history.back().first.first] = history.back().first.second; else siz[history.back().first.first] = history.back().first.second; history.pop_back(); } } }; vector<pair<pair<int,int>,pair<int,int>>> edges; vector<pair<int,int>> begin_on_t[100005],end_on_t[100005]; vector<pair<int,pair<int,int>>> begin_on_poz[100005],end_on_poz[100005]; void add_edge(int tle, int tri, int x, int y) { assert(tle<=tri); assert(x<=y); edges.push_back({{tle,tri},{x,y}}); begin_on_t[tle].push_back({x,y}); end_on_t[tri].push_back({x,y}); begin_on_poz[x].push_back({y,{tle,tri}}); end_on_poz[y].push_back({x,{tle,tri}}); } vector<pair<pair<int,int>,int>> qrys; bool cmp_mo(pair<pair<int,int>,int> x, pair<pair<int,int>,int> y)///-------------------------------------------------------------- { return x<y; } vector<pair<pair<int,int>,pair<int,int>>> dynamic_edges; void add_dynamic_edge(int tle, int tri, int x, int y) { dynamic_edges.push_back({{tle,tri},{x,y}}); } map<pair<int,int>,int> dynamic_time; void baga_dynamic(int t, int x, int y) { if(x>y) swap(x,y); dynamic_time[{x,y}] = t; } void scoate_dynamic(int t, int x, int y) { if(x>y) swap(x,y); if(dynamic_time[{x,y}]) { add_dynamic_edge(dynamic_time[{x,y}],t-1,x,y); dynamic_time[{x,y}] = 0; } } int who[100005]; std::vector<int> simulateCollapse( int N, std::vector<int> T, std::vector<int> X, std::vector<int> Y, std::vector<int> W, std::vector<int> P) { n=N; map<pair<int,int>,int> construction_day; for(int i=0;i<T.size();i++) { if(X[i] > Y[i]) swap(X[i],Y[i]); if(T[i]==0) { construction_day[{X[i],Y[i]}] = i; } else { add_edge(construction_day[{X[i],Y[i]}],i-1,X[i],Y[i]); construction_day[{X[i],Y[i]}] = -1; } } for(auto it:construction_day) { if(it.second != -1) { add_edge(it.second, (int)T.size() + 2, it.first.first, it.first.second); } } for(int i=0;i<W.size();i++) { qrys.push_back({{W[i],P[i]},i}); /*dsu.rollback(0); for(auto [t,e]:edges) { if(t.first <= W[i] && W[i] <= t.second && (e.second <= P[i] || e.first > P[i])) { dsu.unite(e.first, e.second); } } sol[i] = n - dsu.get_time()/2;*/ } sort(qrys.begin(),qrys.end(),cmp_mo); int myt = -1, myp = qrys[0].first.second; for(int i=1;i<=qrys.size();i++) { int w = qrys[i-1].first.first, p = qrys[i-1].first.second, id = qrys[i-1].second; who[i] = id; while(myt < w) { if(myt!=-1) for(auto [x,y]:end_on_t[myt]) scoate_dynamic(i,x,y); myt++; for(auto [x,y]:begin_on_t[myt]) if(y <= p || x > p) baga_dynamic(i,x,y); } while(myt > w) { for(auto [x,y]:begin_on_t[myt]) scoate_dynamic(i,x,y); myt--; for(auto [x,y]:end_on_t[myt]) if(y <= p || x > p) baga_dynamic(i,x,y); } while(myp < p) { myp++; for(auto [other_poz,t]:end_on_poz[myp]) if(t.first <= w && w <= t.second) baga_dynamic(i,other_poz,myp); for(auto [other_poz,t]:begin_on_poz[myp]) scoate_dynamic(i,myp,other_poz); } while(myp > p) { for(auto [other_poz,t]:end_on_poz[myp]) scoate_dynamic(i,other_poz,myp); for(auto [other_poz,t]:begin_on_poz[myp]) if(t.first <= w && w <= t.second) baga_dynamic(i,myp,other_poz); myp--; } } for(auto it:dynamic_time) if(it.second != 0) baga_dynamic((int)qrys.size() + 2, it.first.first, it.first.second); vector<int> sol((int)W.size()); for(int dyn_t=1;dyn_t<=qrys.size();dyn_t++) { int id = who[dyn_t]; DSU dsu; dsu.init(); for(auto [t,e]:dynamic_edges) { if(t.first <= dyn_t && dyn_t <= t.second) { dsu.unite(e.first, e.second); } } sol[id] = n - dsu.get_time()/2; } return sol; }
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...