#122-[樹形動態規劃]LazyChild黑OJ
阿新 • • 發佈:2018-11-09
Description
LazyChild開了一家“善良OJ”。但大多數人都不知道,這其實是家黑OJ。親愛的同學,請不要驚訝,古時候有黑店,現代為什麼不能有黑OJ呢?每AC一道題,網站便會自動在電腦上安裝一種木馬。LazyChild通過竊取資訊獲取收益(如網遊帳號、OI資料、YuanY和TT的照片等等)。
作為一名資深黑客,老Z某日突然發現,“善良OJ”上的木馬,自己電腦上都沒有。這可十分讓他過意不去。老Z決定通過多A題,來豐富自己電腦的病毒庫。
經過調查,老Z發現,很多木馬是不能共存的。比如“和諧”木馬與“團結”木馬,兩者只能任選其一。然而,老Z是個完美主義者,他想要自己的病毒庫儘可能充實。
老Z不懈的追求最終感動了上天。天上的神仙(半仙?)“牛人雨”給這個問題稍稍降低了一點難度。神仙規定,對於n種木馬,有且僅有(n-1)對不能共存,並且對於每種木馬,都存在至少一個木馬與之不能共存。
老Z不在乎自己AC多少題。請告訴他,他最多能從“善良OJ”上獲取木馬的個數。
Input
第一行,一個正整數n,表示木馬個數。
剩餘(n-1)行,每行一對木馬,表示他們不能共存。(保證相同的木馬可以共存,任意不同兩行的描述不等價)
木馬編號從0至(n-1)
Output
一行,老Z最多獲得木馬的個數。你可以認為開始時沒有任何木馬。
Sample Input
3 0 1 1 2
Sample Output
2
HINT
【資料規模】
對於100%的資料,1<=n<=200
如果這個點選了,它的兒子就不能選.
否則隨便.
#include <iostream> #include <vector> #define SIZE 210 using namespace std; vector<int> graph[SIZE]; int dp[SIZE][2]; void dfs(int u, int pre) // DP過程 { int i, v; dp[u][1] = 1; // 邊界條件 for (i = 0; i < graph[u].size(); ++i) { v = graph[u][i]; if (v != pre) { dfs(v, u); dp[u][0] += max(dp[v][0], dp[v][1]); // 如果這個點沒選,它的兒子選不選隨便 dp[u][1] += dp[v][0]; // 如果這個點選了,它的兒子就不能選. } } return; } int main(int argc, char** argv) { int n, u, v; scanf("%d", &n); while (--n) { scanf("%d%d", &u, &v); graph[u].push_back(v); // 建圖 graph[v].push_back(u); } dfs(0, -1); printf("%d", max(dp[0][0], dp[0][1])); return 0; }