樹形dp TT的蘋果樹

2021-10-06 16:38:35 字數 2494 閱讀 9517

在大家的三連助攻下,tt 一舉獲得了超級多的貓咪,因此決定開一間貓咖,將快樂與大家一同分享。並且在開業的那一天,為了紀念這個日子,tt 在貓咖門口種了一棵蘋果樹。

一年後,蘋果熟了,到了該摘蘋果的日子了。

已知樹上共有 n 個節點,每個節點對應乙個快樂值為 w[i] 的蘋果,為了可持續發展,tt 要求摘了某個蘋果後,不能摘它父節點處的蘋果。

tt 想要令快樂值總和盡可能地大,你們能幫幫他嗎?

input

結點按 1~n 編號。

第一行為 n (1 ≤ n ≤ 6000) ,代表結點個數。

接下來 n 行分別代表每個結點上蘋果的快樂值 w[i](-128 ≤ w[i] ≤ 127)。

接下來 n-1 行,每行兩個數 l k,代表 k 是 l 的乙個父節點。

輸入有多組,以 0 0 結束。

output

每組資料輸出乙個整數,代表所選蘋果快樂值總和的最大值。

輸入樣例71

1111

111 37 4

2 34 5

6 43 5

0 0輸出樣例

5對於在樹結構上進行的動態規劃叫做樹形dp,由於樹的性質,一般採用遞迴進行。

對於這道題,按照要求採取的果子在樹上的距離應該大於等於2,即採取了某個果子,那麼這個果子的父節點和子節點都不能取。

dp[i][1/0]代表以i為節點的子樹能達到的最大的氣氛值,dp[i][1]代表i節點擊了,dp[i][0]代表i節點沒選,狀態轉移方程是

若是父節點擊了,那麼子節點一定不能選,若是父節點沒選,子節點可選可不選。

為了減少呼叫函式的次數,即為了減少重複的對某個節點dp值得計算,設立乙個陣列vis[i][0/1],vis[i][0] == true代表i號節點不選的值已經計算過,直接在陣列中呼叫即可,vis[i][1] == true代表i號節點擊則的值已經計算過。

#include

#include

#include

using

namespace std;

//dp[i][1/0]代表以i為節點的子樹能達到的最大的氣氛值

//dp[i][1]代表i節點擊了

//dp[i][0]代表i節點沒選

struct edge

edge[

6005];

int head[

6005];

long

long tot;

bool vis[

6005][

2];//[0]代表不取,[1]代表取

void

add(

int u,

int v)

int dp[

6005][

2];int w[

6005];

bool isroot[

6005];

void

thisnotget

(int);

void

thisget

(int now)

}void

thisnotget

(int now)

}int

main()

tot =0;

memset

(dp,0,

sizeof

(dp));

memset

(head,-1

,sizeof

(head));

memset

(w,0

,sizeof

(w))

;memset

(isroot,

true

,sizeof

(isroot));

memset

(vis,

false

,sizeof

(vis));

for(

int i =

1; i <= n; i++

) cin >> w[i]

;for

(int i =

1; i < n; i++

)int root;

for(

int i =

1; i <= n; i++)if

(isroot[i]

)root = i;

thisget

(root)

;thisnotget

(root);if

(dp[root][0

]> dp[root][1

])cout << dp[root][0

]<< endl;

else cout << dp[root][1

]<< endl;

}}

樹形揹包 蘋果樹

題目大意 求乙個聯通點集點權和 m leq m m的最大點的個數。這道題是乙個樹形揹包問題,以點的個數為體積,以體積為價值 然後我們只要找到體積 m le m m的最大點數即可。我們設f i j f i j f i j 表示以i ii為根的子樹中,一定選第i ii個點且選了j jj個點的最小花費。若...

二叉蘋果樹 樹形DP

題意 description 有一棵蘋果樹,如果樹枝有分叉,一定是分2叉 就是說沒有只有1個兒子的結點 這棵樹共有n個結點 葉子點或者樹枝分叉點 編號為1 n,樹根編號一定是1。我們用一根樹枝兩端連線的結點的編號來描述一根樹枝的位置。下面是一顆有4個樹枝的樹 2 5 3 4 1 現在這顆樹枝條太多了...

樹形DP 二叉蘋果樹

有一棵二叉蘋果樹,如果樹枝有分叉,一定是分兩叉,即沒有只有乙個兒子的節點。這棵樹共 n 個節點,編號為 1 至 n,樹根編號一定為 1。我們用一根樹枝兩端連線的節點編號描述一根樹枝的位置。一棵蘋果樹的樹枝太多了,需要剪枝。但是一些樹枝上長有蘋果,給定需要保留的樹枝數量,求最多能留住多少蘋果。這裡的保...