Submission #546427

#TimeUsernameProblemLanguageResultExecution timeMemory
546427cadmiumskyMeetings 2 (JOI21_meetings2)C++14
100 / 100
3688 ms48768 KiB
#include <bits/stdc++.h> #pragma GCC optimize("fast-math") #pragma GCC optimize("Ofast") #pragma GCC target("sse3,sse4,avx,avx2") #pragma GCC push_options #pragma GCC pop_options using namespace std; const int nmax = 2e5 + 5; vector<int> g[nmax]; int n; int rez[nmax]; int supmem[nmax + 100], ptr; namespace Centroid { int occ[nmax]; int area[nmax]; int nval[nmax]; int depth[nmax]; #define norm lasama map<pair<int, int> ,int> norm; map<int ,int> fpoz; namespace AINT { int aint[1048576]; static int len; void clean(int node = 1, int cl = 1, int cr = len) { aint[node] = 0; if(cl == cr) return; int mid = cl + cr >> 1; clean(2 * node, cl, mid); clean(2 * node + 1, mid + 1, cr); } void init(int nlen) { len = nlen; clean(); } void upd(int poz, int val, int node = 1, int cl = 1, int cr = len) { if(cl == cr) aint[node] = val; else { int mid = cl + cr >> 1; if(poz <= mid) upd(poz, val, 2 * node, cl, mid); else upd(poz, val, 2 * node + 1, mid + 1, cr); aint[node] = max(aint[2 * node], aint[2 * node + 1]); } return; } int query(int poz, int node = 1, int cl = 1, int cr = len) { if(cr < poz) return 0; if(poz <= cl) return aint[node]; int mid = cl + cr >> 1; return max(query(poz, 2 * node, cl, mid), query(poz, 2 * node + 1, mid + 1, cr)); } }; void initcentr(int node, int f) { area[node] = 1; for(auto x : g[node]) { if(occ[x] == 0 && x != f) initcentr(x, node), area[node] += area[x]; } return; } int initdepth(int node, int f) { if(occ[node]) return area[node]; depth[node] = depth[f] + 1; area[node] = 1; for(auto x : g[node]) if(x != f) area[node] += initdepth(x, node); return area[node]; } int findcentr(int node, int f, int thresh) { for(auto x : g[node]) { if(occ[x] || x == f) continue; if(area[x] > thresh) return findcentr(x, node, thresh); } return node; } void aggr(int node, int f, int val) { if(val == -1) AINT::upd(nval[node], 0); else AINT::upd(nval[node], depth[node]); for(auto x : g[node]) if(!occ[x] && x != f) aggr(x, node, val); } void bnorm(int node, int f) { norm[{area[node], node}]; for(auto x : g[node]) if(!occ[x] && x != f) bnorm(x, node); return; } void query(int node, int f) { int x = AINT::query(fpoz[area[node]]); if(x > 0) rez[(area[node]) * 2] = max(rez[(area[node]) * 2], x + depth[node] - 1); for(auto x : g[node]) if(!occ[x] && x != f) query(x, node); return; } void mkcentr(int node) { //cerr << "++++++\n" << node << "\n=====\n"; int temp; initcentr(node, node); node = findcentr(node, node, area[node] / 2); //cerr << "Centroid is: " << node << '\n'; depth[node] = 0; initdepth(node, node); for(int x, i = 0; i < g[node].size(); i++) { if(occ[g[node][i]]) { swap(g[node][i], g[node].back()); g[node].pop_back(); i--; continue; } x = g[node][i]; norm[{n - area[x], node}]; bnorm(x, node); } temp = 0; for(auto &[a, b] : norm) { b = ++temp; if(fpoz.find(a.first) == fpoz.end()) fpoz[a.first] = b; nval[a.second] = b; } if(temp != 0) { AINT::init(temp); for(int i = 0; i < g[node].size(); i++) aggr(g[node][i], node, 1); for(int i = 0, x; i < g[node].size(); i++) { x = g[node][i]; aggr(x, node, -1); AINT::upd(temp = norm[{n - area[x], node}], depth[node]); query(x, node); AINT::upd(temp, 0); aggr(x, node, 1); } } fpoz.clear(); norm.clear(); occ[node] = 1; int L = ptr, R; for(auto x : g[node]) supmem[ptr++] = area[x]; R = ptr; for(auto x : g[node]) { area[node] = n - supmem[L++]; mkcentr(x); } } } int what[nmax]; mt19937 rng(time(0)); int rnd(int x) { return rng() % x; } int main() { srand(time(0)); cin >> n; for(int i = 1; i <= n; i++) what[i] = i; random_shuffle(what + 1, what + n + 1, rnd); for(int x, y, i = 1; i < n; i++) { cin >> x >> y; x = what[x]; y = what[y]; g[x].push_back(y); g[y].push_back(x); } Centroid::mkcentr(1); for(int i = n; i > 0; i--) { if(i % 2 == 0) rez[i] = max({1, rez[i + 2], rez[i]}); else rez[i] = 1; } //cout << "1\n" << 2 + rez[2] << '\n'; for(int i = 1; i <= n; i++) cout << rez[i] << '\n'; }

Compilation message (stderr)

meetings2.cpp: In function 'void Centroid::AINT::clean(int, int, int)':
meetings2.cpp:29:20: warning: suggest parentheses around '+' inside '>>' [-Wparentheses]
   29 |       int mid = cl + cr >> 1;
      |                 ~~~^~~~
meetings2.cpp: In function 'void Centroid::AINT::upd(int, int, int, int, int)':
meetings2.cpp:41:22: warning: suggest parentheses around '+' inside '>>' [-Wparentheses]
   41 |         int mid = cl + cr >> 1;
      |                   ~~~^~~~
meetings2.cpp: In function 'int Centroid::AINT::query(int, int, int, int)':
meetings2.cpp:55:20: warning: suggest parentheses around '+' inside '>>' [-Wparentheses]
   55 |       int mid = cl + cr >> 1;
      |                 ~~~^~~~
meetings2.cpp: In function 'void Centroid::mkcentr(int)':
meetings2.cpp:115:25: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
  115 |     for(int x, i = 0; i < g[node].size(); i++) {
      |                       ~~^~~~~~~~~~~~~~~~
meetings2.cpp:127:15: warning: structured bindings only available with '-std=c++17' or '-std=gnu++17'
  127 |     for(auto &[a, b] : norm) {
      |               ^
meetings2.cpp:135:24: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
  135 |       for(int i = 0; i < g[node].size(); i++)
      |                      ~~^~~~~~~~~~~~~~~~
meetings2.cpp:137:27: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
  137 |       for(int i = 0, x; i < g[node].size(); i++) {
      |                         ~~^~~~~~~~~~~~~~~~
meetings2.cpp:149:18: warning: variable 'R' set but not used [-Wunused-but-set-variable]
  149 |     int L = ptr, R;
      |                  ^
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...