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 "towns.h"
#include <vector>
#include <cmath>
#include <set>
#include <iostream>
#include <cassert>
using namespace std;
namespace
{
using vi = vector<int>;
#define sz(x) int(x.size())
int ST, best_coord;
vi xcoord;
int S;
int T;
vi distS, dist0;
int qrc;
}
int best_dist(int i)
{
int height = (distS[i] + dist0[i] - distS[0])/2;
return height + abs(xcoord[i] - best_coord);
}
int areequal(int i, int j)
{
return getDistance(i, j) != best_dist(i) + best_dist(j);
}
const int mx = 110;
struct dsu
{
vi parent;
vi subtree;
dsu()
{
parent = subtree = vi(mx);
for(int i = 0; i < mx; i++)
{
parent[i] = i;
subtree[i] = 1;
}
}
int root(int u)
{
if(parent[u] == u) return u;
else return parent[u] = root(parent[u]);
}
void join(int u, int v)
{
u = root(u);
v = root(v);
if(u == v) return;
if(subtree[u] < subtree[v])
swap(u, v);
parent[v] = u;
subtree[u] += subtree[v];
}
};
int hubDistance(int N, int sub)
{
qrc = 0;
dist0 = vi(N);
dist0[0] = 0;
for(int i = 1; i < N; i++)
dist0[i] = getDistance(0, i);
S = 0;
for(int i = 1; i < N; i++)
if(dist0[i] > dist0[S])
S = i;
ST = 0; //diameter
// cerr << "done\n";
distS = vi(N);
distS[S] = 0;
distS[0] = dist0[S];
T = 0;
ST = distS[0];
for(int i = 1; i < N; i++)
{
if(i != S)
{
distS[i] = getDistance(S, i);
if(distS[i] > ST)
{
ST = distS[i];
T = i;
}
}
}
// cerr << "S = " << S << "\n";
vi S0_dist(N);
for(int i = 0; i < N; i++)
S0_dist[i] = (distS[i] + dist0[i] - distS[0])/2;
xcoord = vi(N);
for(int i = 0; i < N; i++)
xcoord[i] = distS[i] - S0_dist[i];
int dist0_ST = (dist0[S] + dist0[T] - ST)/2;
int ST_0coord = dist0[S] - dist0_ST;
assert(2*ST_0coord >= distS[T]);
// assert((dist0[S] + getDistance(0, T) - distS[T]) <= distS[T])
int res = 5'000'000;
set<int> best_coords;
for(int i = 0; i < N; i++)
{
if(xcoord[i] > ST_0coord)
continue;
int curr = max(xcoord[i], ST - xcoord[i]);
if(curr < res)
{
res = curr;
best_coords.clear();
}
if(curr == res)
{
best_coords.insert(xcoord[i]);
}
}
if(sz(best_coords) == 1)
{
best_coord = *best_coords.begin();
}
else
{
int leftcount = 0;
for(int i = 0; i < N; i++)
{
if(xcoord[i] <= *best_coords.begin())
leftcount++;
}
if(2*leftcount >= N)
best_coord = *best_coords.begin();
else
best_coord = *best_coords.rbegin();
}
// return -res;
dsu DSU;
bool balanced = 1;
int candidate = -1;
int counter = 0;
for(int i = 0; i < N; i++)
{
if(counter == 0)
{
candidate = i;
counter = 1;
}
else
{
if(areequal(i, candidate))
{
counter++;
DSU.join(i, candidate);
}
else
{
counter--;
}
}
}
vi checked(N, 0);
checked[DSU.root(candidate)] = 0;
for(int i = 0; i < N; i++)
{
if(checked[DSU.root(i)] == 0)
{
if(areequal(DSU.root(i), candidate))
checked[DSU.root(i)] = 1;
else
checked[DSU.root(i)] = -1;
}
}
int ct = 0;
for(int i = 0; i < N; i++)
ct += (checked[DSU.root(i)] == 1);
balanced = (2*ct <= N);
int R = res;
if(balanced)
return R;
else
return -R;
}
Compilation message (stderr)
towns.cpp: In function 'int hubDistance(int, int)':
towns.cpp:81:28: warning: unused parameter 'sub' [-Wunused-parameter]
81 | int hubDistance(int N, int sub)
| ~~~~^~~
# | 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... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |