Cod sursa(job #587680)

Utilizator tamas_iuliaTamas Iulia tamas_iulia Data 5 mai 2011 16:20:09
Problema Guvern Scor 70
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.95 kb
#include <stdio.h>
#include <set>
#include <vector>
#define pb push_back
#define mp make_pair
#define ff first.first
#define fs first.second
#define ss second
#define piii pair< pair<int,int> , int >
#define Nmax 200005
using namespace std;

set< piii > Set;
vector< int > v[Nmax],vdd[Nmax];
int TT[Nmax],TTdd[Nmax],Nr[Nmax],Cost[Nmax],Din[Nmax],F[Nmax],L[Nmax];
int N,nr_df;

inline void df(int x){
    vector< int >:: iterator it;
    set< piii >:: iterator wh;
    Nr[x] = ++nr_df;
    F[x] = nr_df;
    Set.insert(mp(mp(Cost[x],-Nr[x]),x));

    for(it=v[x].begin(); it!=v[x].end(); ++it)
        if( *it != TT[x] ){
            wh = Set.upper_bound( mp( mp(Cost[*it]-1,0 ),0) );
            if( wh != Set.end() )
                TTdd[*it] = wh->ss;

            TT[*it]=x;
            df(*it);
        }

    L[x] = ++nr_df;
    Set.erase(mp(mp(Cost[x],-Nr[x]),x));
}

inline void df2(int x){
    int ttdd,sum;
    vector< int >:: iterator it;

    for(it=v[x].begin(); it!=v[x].end(); ++it)
        if( *it != TT[x] )
            df2(*it);

    Din[x]=1;
    if( ! vdd[x].empty() ){
        for(it=vdd[x].begin(); it!=vdd[x].end(); ++it)
            Din[x] += Din[*it];
    }

    if( TTdd[x] == 0 ) return;

    ttdd=TTdd[x]; sum=0;
    while( !vdd[ttdd].empty() && F[vdd[ttdd].back()]>F[x] && L[vdd[ttdd].back()]<L[x] ){
        sum += Din[vdd[ttdd].back()];
        vdd[ttdd].pop_back();
    }
    if( sum > Din[x] ) Din[x]=sum;
    vdd[ttdd].pb(x);
}

int main(){
    int i,sol,x,y;
    freopen("guvern.in","r",stdin);
    freopen("guvern.out","w",stdout);
    scanf("%d",&N);
    for(i=1;i<N;++i){
        scanf("%d%d",&x,&y);
        v[x].pb(y);
        v[y].pb(x);
    }
    for(i=1;i<=N;++i)
        scanf("%d",&Cost[i]);

    df(1);
    df2(1);

    sol=0;
    for(i=1;i<=N;++i)
        if( Din[i] > sol ) sol=Din[i];

    printf("%d\n",sol);
    fclose(stdin); fclose(stdout);
    return 0;
}