# | Time | Username | Problem | Language | Result | Execution time | Memory |
---|---|---|---|---|---|---|---|
603150 | definitelynotmee | Split the Attractions (IOI19_split) | C++17 | 220 ms | 42760 KiB |
This submission is migrated from previous version of oj.uz, which used different machine for grading. This submission may have different result if resubmitted.
#include "split.h"
#include <bits/stdc++.h>
using namespace std;
using ll = long long;
using pii = pair<int,int>;
using pll = pair<ll,ll>;
template<typename T> using matrix = vector<vector<T>>;
#define ff first
#define ss second
#define all(x) x.begin(), x.end()
vector<int> find_split(int n, int a, int b, int c, vector<int> p, vector<int> q) {
matrix<int> g(n), tree(n);
for(int i = 0; i < p.size(); i++)
g[p[i]].push_back(q[i]), g[q[i]].push_back(p[i]);
vector<int> sub(n), low(n);
matrix<int> indep(n), dep(n);
vector<int> pai(n,n/2);
int cen = 0;
vector<int> tin(n);
int timer = -1;
auto dfs =[&](int id, auto dfs)->void{
sub[id] = 1;
tin[id] = ++timer;
low[id] = tin[id];
int maxi = 0;
for(int i : g[id]){
if(sub[i]){
low[id] = min(low[id],tin[i]);
continue;
}
tree[id].push_back(i);
tree[i].push_back(id);
pai[i] = id;
indep[i].push_back(id);
dfs(i,dfs);
int cur = sub[i];
maxi = max(maxi,cur);
sub[id] += cur;
if(low[i] < tin[id])
indep[id].push_back(i);
else dep[id].push_back(i);
low[id] = min(low[id],low[i]);
}
maxi = max(maxi,n-sub[id]);
if(maxi <= n/2)
cen = id;
};
dfs(n/2,dfs);
sub[pai[cen]] = n-sub[pai[cen]];
vector<int> v = {a,b,c};
vector<int> o = {0,1,2};
sort(all(o),[&](int a, int b){
return v[a] < v[b];
});
vector<int> sz = {v[o[0]],v[o[1]], v[o[2]]};
array<vector<int>,3> group;
vector<int> resp(n,2);
auto filltree =[&](int id, int last, int color, auto dfs)->void{
group[color].push_back(id);
resp[id] = color;
for(int i : tree[id]){
if(i == last || resp[i] !=2)
continue;
if(group[color].size() < sz[color])
dfs(i,id,color,dfs);
}
};
auto fillgraph =[&](int id, int color, auto dfs)->void{
group[color].push_back(id);
resp[id] = color;
for(int i : g[id]){
if(resp[i] != 2)
continue;
if(group[color].size() < sz[color])
dfs(i,color,dfs);
}
};
auto buildresp =[&](){
for(int& i : resp)
i = o[i]+1;
};
for(int i : tree[cen]){
if(sub[i] >= sz[0]){
filltree(i,cen,0,filltree);
fillgraph(cen,1,fillgraph);
buildresp();
assert(group[0].size() == sz[0] && group[1].size() == sz[1]);
return resp;
}
}
int depsize = 1;
for(int i : dep[cen])
depsize+=sub[i];
if(depsize >= sz[1]){
if(n-depsize >= sz[0]){
group[1].push_back(cen);
resp[cen] = 1;
for(int i : dep[cen]){
if(group[1].size() < sz[1])
filltree(i,cen,1,filltree);
}
fillgraph(indep[cen].back(),0,fillgraph);
buildresp();
assert(group[0].size() == sz[0] && group[1].size() == sz[1]);
} else resp = vector<int>(n);
return resp;
}
group[0].push_back(cen);
resp[cen] = 0;
for(int i : dep[cen]){
if(group[0].size() < sz[0])
filltree(i,cen,0,filltree);
}
while(group[0].size() < sz[0]){
filltree(indep[cen].back(),cen,0,filltree);
indep[cen].pop_back();
}
assert(!indep[cen].empty());
fillgraph(indep[cen].back(),1,fillgraph);
buildresp();
assert(group[0].size() == sz[0] && group[1].size() == sz[1]);
return resp;
}
Compilation message (stderr)
# | Verdict | Execution time | Memory | Grader output |
---|---|---|---|---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|---|---|---|---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|---|---|---|---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|---|---|---|---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|---|---|---|---|
Fetching results... |