D. Sum in the tree codeforces round#530(div2)

对于偶数层,取下面节点的最小值,然后下面节点都减去最小值即可

#include<bits/stdc++.h>
using namespace std;
int p[200010];
int s[200010];
int h[200010];
int a[200010];
vector<int> vec[200010];
long long res=0;
const int INF=1e9+7;
void dfs(int num,int dep)
{
    if(dep%2==1)
    {
        res+=a[num];
    }
    else
    {
        int mina=INF;
        for(int i=0;i<vec[num].size();i++)
        {
            int node=vec[num][i];
            mina=min(a[node],mina);
        }
        for(int i=0;i<vec[num].size();i++)
        {
            int node=vec[num][i];
            a[node]-=mina;
        }
        if(mina!=INF)
           res+=mina;
    }
    for(int i=0;i<vec[num].size();i++)
       dfs(vec[num][i],dep+1);
}
int main()
{
    int n;
    scanf("%d",&n);
    for(int i=2;i<=n;i++)
    {
        scanf("%d",&p[i]);
    }
    for(int i=1;i<=n;i++)
    {
        scanf("%d",&s[i]);
    }
    h[1]=1;
    for(int i=2;i<=n;i++)
    {
        h[i]=h[p[i]]+1;
    }
    for(int i=2;i<=n;i++)
    {
        if(h[i]%2==1)
        {
            int fa=p[p[i]];
            if(s[fa]>s[i])
            {
                printf("-1
");
                return 0;
            }
        }
    }
    a[1]=s[1];
    for(int i=2;i<=n;i++)
    {
        vec[p[i]].push_back(i);
        if(h[i]%2==1)
        {
            int fa=p[p[i]];//减去上两层的父节点 
            a[i]=s[i]-s[fa];
        }
    }
    dfs(1,1);//如果是奇数层直接加,如果是偶数层考虑下面每个节点的最小值 
    printf("%lld
",res);
}
原文地址:https://www.cnblogs.com/lishengkangshidatiancai/p/10244854.html