沒有上司的舞會 樹形dp
阿新 • • 發佈:2019-02-04
經典的 分享 \n clu 1.0 can map 描述 rds
輸出格式:
題目描述
某大學有N個職員,編號為1~N。他們之間有從屬關系,也就是說他們的關系就像一棵以校長為根的樹,父結點就是子結點的直接上司。現在有個周年慶宴會,宴會每邀請來一個職員都會增加一定的快樂指數Ri,但是呢,如果某個職員的上司來參加舞會了,那麽這個職員就無論如何也不肯來參加舞會了。所以,請你編程計算,邀請哪些職員可以使快樂指數最大,求最大的快樂指數。
輸入輸出格式
輸入格式:第一行一個整數N。(1<=N<=6000)
接下來N行,第i+1行表示i號職員的快樂指數Ri。(-128<=Ri<=127)
接下來N-1行,每行輸入一對整數L,K。表示K是L的直接上司。
最後一行輸入0 0
輸出最大的快樂指數。
輸入輸出樣例
輸入樣例#1: 復制7 1 1 1 1 1 1 1 1 3 2 3 6 4 7 4 4 5 3 5 0 0輸出樣例#1: 復制
5
經典的樹形dp;
dp[x][0] 表示x的子樹,不選 x 所能得到的最大值;
dp[x][1]表示選 x 得到的最大值;
#include<iostream> #include<cstdio> #include<algorithm> #include<cstdlib> #include<cstring> #include<string> #include<cmath> #include<map> #include<set> #include<vector> #include<queue> #include<bitset> #include<ctime> #include<deque> #include<stack> #include<functional> #include<sstream> //#include<cctype> //#pragma GCC optimize(2) using namespace std; #define maxn 200005 #define inf 0x7fffffff //#define INF 1e18 #define rdint(x) scanf("%d",&x) #define rdllt(x) scanf("%lld",&x) #define rdult(x) scanf("%lu",&x) #define rdlf(x) scanf("%lf",&x) #define rdstr(x) scanf("%s",x) typedef long long ll; typedef unsigned long long ull; typedef unsigned int U; #define ms(x) memset((x),0,sizeof(x)) const long long int mod = 1e9; #define Mod 1000000000 #define sq(x) (x)*(x) #define eps 1e-5 typedef pair<int, int> pii; #define pi acos(-1.0) //const int N = 1005; #define REP(i,n) for(int i=0;i<(n);i++) typedef pair<int, int> pii; inline int rd() { int x = 0; char c = getchar(); bool f = false; while (!isdigit(c)) { if (c == ‘-‘) f = true; c = getchar(); } while (isdigit(c)) { x = (x << 1) + (x << 3) + (c ^ 48); c = getchar(); } return f ? -x : x; } ll gcd(ll a, ll b) { return b == 0 ? a : gcd(b, a%b); } int sqr(int x) { return x * x; } /*ll ans; ll exgcd(ll a, ll b, ll &x, ll &y) { if (!b) { x = 1; y = 0; return a; } ans = exgcd(b, a%b, x, y); ll t = x; x = y; y = t - a / b * y; return ans; } */ int n; int hp[maxn]; int dp[maxn][2]; vector<int>vc[maxn]; bool fg[maxn]; int rt; int ans; void dfs(int root) { dp[root][0] = 0; dp[root][1] = hp[root]; for (int i = 0; i < vc[root].size(); i++) { int v = vc[root][i]; dfs(v); dp[root][0] += max(dp[v][0], dp[v][1]); dp[root][1] += dp[v][0]; } return; } int main() { //ios::sync_with_stdio(0); n = rd(); for (int i = 1; i <= n; i++)hp[i] = rd(); for (int i = 1; i < n; i++) { int u, v; u = rd(); v = rd(); vc[v].push_back(u); fg[u] = 1; } int x, y; x = rd(); y = rd(); for (int i = 1; i <= n; i++) { if (!fg[i]) { rt = i; break; } } dfs(rt); printf("%d\n", max(dp[rt][0], dp[rt][1])); return 0; }
沒有上司的舞會 樹形dp