Cod sursa(job #3266091)

Utilizator RaresPoinaruPoinaru-Rares-Aurel RaresPoinaru Data 5 ianuarie 2025 17:38:58
Problema Heavy Path Decomposition Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.66 kb
#include <bits/stdc++.h>
using namespace std;
ifstream fin ("heavypath.in");
ofstream fout ("heavypath.out");
const int MAXN=2e5+10;


int n,a[MAXN],q,s[MAXN],radacina[MAXN],pos[MAXN],t,tata[MAXN];
int nivel[MAXN];
vector <int> g[MAXN];
int aint[4*MAXN];

void dfs (int node, int prevn){
    s[node]=1;
    tata[node]=prevn;
    nivel[node]=nivel[prevn]+1;
    for (auto x:g[node]){
        if (x==prevn) continue;
        dfs (x,node);
        s[node]+=s[x];
    }
}
void crearelant (int node){
    pos[node]=++t;
    int maxx=0,nextn=0;
    for (auto x:g[node]){
        if (radacina[x]) continue;
        if (s[x]>maxx){
            maxx=s[x];
            nextn=x;
        }
    }
    if (nextn){
        radacina[nextn]=radacina[node];
        crearelant (nextn);
        for (auto x:g[node]){
            if (radacina[x]) continue;
            radacina[x]=x;
            crearelant (x);
        }
    }

}

void update (int node, int l, int r, int pos, int val){
    if (l==r){
        aint[node]=val;
        return;
    }
    int mij=(l+r)/2;
    if (mij>=pos) update (2*node,l,mij,pos,val);
    else update (2*node+1,mij+1,r,pos,val);
    aint[node]=max (aint[2*node],aint[2*node+1]);
}
void update (int pos, int val){
    update (1,1,n,pos,val);
}
int query (int node, int l, int r, int ql, int qr){
    if (r<ql or l>qr) return 0;
    if (ql<=l and r<=qr)
        return aint[node];
    int mij=(l+r)/2;
    int rez1=query (2*node,l,mij,ql,qr);
    int rez2=query (2*node+1,mij+1,r,ql,qr);
    return max (rez1,rez2);
}
int query (int l, int r){
    if (l>r) swap (l,r);
    return query (1,1,n,l,r);
}
int querypath (int x, int y){
    int rez=0;
    while (radacina[x]!=radacina[y]){
        if (nivel[radacina[x]]<nivel[radacina[y]]) swap (x,y);
        rez=max (rez,query (pos[x],pos[radacina[x]]));
        x=tata[radacina[x]];
    }
    rez=max (rez,query (pos[x],pos[y]));
    return rez;
}

int main()
{
    ios_base::sync_with_stdio (false);
    cin.tie (nullptr);
    fin >>n>>q;
    for (int i=1;i<=n;++i){
        fin >>a[i];
    }
    for (int i=1;i<n;++i){
        int x,y;
        fin >>x>>y;
        g[x].push_back (y);
        g[y].push_back (x);
    }

    dfs (1,1);

    radacina[1]=1;
    crearelant (1);
    for (int i=1;i<=n;++i){
        update (pos[i],a[i]);
    }

    for (int i=1;i<=q;++i){
        int c,x,y;
        fin >>c>>x>>y;
        if (c==0){

            update (pos[x],y);

            a[x]=y;
        }
        else{
            fout <<querypath (x,y)<<'\n';
        }
    }
    return 0;
}
/*
5 3
2 4 1 3 3
1 2
1 3
2 4
2 5
2 2 2
1 2 2
2 2 2
*/