Submission #398279

#TimeUsernameProblemLanguageResultExecution timeMemory
398279Jarif_RahmanMeetings 2 (JOI21_meetings2)C++17
100 / 100
1119 ms97444 KiB
#include <bits/stdc++.h>
#define pb push_back
#define f first
#define sc second
using namespace std;
typedef long long int ll;
typedef string str;

int n;

vector<vector<int>> v;
vector<int> ans;
vector<set<pair<int, int>>> s;
vector<int> sz;
vector<multiset<int>> ms;
vector<vector<int>> anc;

int get_anc(int nd, int ss){
    for(int i = 1; i < 20; i++){
        if(ss%2 == 1) nd = anc[nd][i];
        if(nd == -1) return -1;
        ss/=2;
    }
    return nd;
}

int sth(int nd, int szz, int dis){
    if(dis == 0) return -1;
    int a = 0, b = dis;
    if(sz[nd] > szz) return -1;
    while(a < b){
        int md = (a+b+1)/2;
        if(sz[get_anc(nd, md)] > szz) b = md-1;
        else a = md;
    }
    return a;
}

void dfs_sz(int nd, int ss){
    for(int x: v[nd]) if(x != ss) dfs_sz(x, nd);
    for(int x: v[nd]) if(x != ss) sz[nd]+=sz[x];
    anc[nd][1] = ss;
}

void dfs(int nd, int ss, int dis, bool keep){
    int mx = 0, in = -1;
    for(int x: v[nd]) if(x != ss && sz[x] > mx) mx = sz[x], in = x;
    for(int x: v[nd]) if(x != ss && x != in) dfs(x, nd, dis+1, 0);
    if(in != -1){
        dfs(in, nd, dis+1, 1);
        swap(s[nd], s[in]);
    }
    for(int x: v[nd]) if(x != ss){
        for(auto [szz0, d0]: s[x]){
            int d = d0, szz = szz0;
            if(n-sz[x] >= szz) ans[szz] = max(ans[szz], d-dis+1);
            if(!ms[szz].empty()){
                int cur = *ms[szz].rbegin();
                cur+=d;
                cur-=2*dis;
                cur++;
                ans[szz] = max(ans[szz], cur);
            }
        }
        for(auto [szz0, d0]: s[x]){
            int d = d0, szz = szz0;
            auto it = s[nd].lower_bound(make_pair(szz, 0));
            if(it == s[nd].end() || it->f != szz){
                s[nd].insert({szz, d});
                ms[szz].insert(d);
            }
            else if(it->sc < d){
                ms[szz].erase(ms[szz].find(it->sc));
                s[nd].erase(it);
                s[nd].insert({szz, d});
                ms[szz].insert(d);
            }
        }
        s[x].clear();
    }
    int szz = n-sz[nd]+1;
    if(!ms[szz].empty()) ans[szz] = max(ans[szz], (*ms[szz].rbegin())-dis+1);
    for(int i = mx+1; i <= sz[nd]; i++){
        ms[i].insert(dis);
        s[nd].insert({i, dis});
        int anc = sth(nd, n-i, dis);
        if(anc != -1){
            anc+=2;
            ans[i] = max(ans[i], anc);
        }
    }
    if(!keep){
        for(auto [szz0, d0]: s[nd]){
            int d = d0, szz = szz0;
            ms[szz].erase(ms[szz].find(d));
        }
    }
}

int main(){
    ios_base::sync_with_stdio(0);
    cin.tie(0);
    cin >> n;
    v.resize(n);
    ans.resize(n+1, 1);
    sz.resize(n, 1);
    s.resize(n);
    ms.resize(n+1);
    anc.resize(n, vector<int>(20, -1));
    for(int i = 0; i < n-1; i++){
        int a, b; cin >> a >> b; a--, b--;
        v[a].pb(b);
        v[b].pb(a);
    }
    dfs_sz(0, -1);

    for(int i = 0; i < n; i++) anc[i][0] = i;

    for(int i = 2; i < 20; i++) for(int j = 0; j < n; j++){
        if(anc[j][i-1] == -1) continue;
        anc[j][i] = anc[anc[j][i-1]][i-1];
    }

    dfs(0, -1, 0, 1);
    for(int i = n-1; i >= 0; i--) ans[i] = max(ans[i], ans[i+1]);
    for(int i = 1; i <= n; i++){
        if(i%2 == 0) cout << ans[i/2] << "\n";
        else cout << "1\n";
    }
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...