Submission #556826

#TimeUsernameProblemLanguageResultExecution timeMemory
556826blueTowns (IOI15_towns)C++17
100 / 100
17 ms840 KiB
#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 timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...