HDU 2196 树形DP

来源:互联网 发布:linux设置目录的权限 编辑:程序博客网 时间:2024/06/07 02:58

题意

N台计算机,N-1条线相连,问这N台计算机每一台计算机到另一台计算机的最长距离是多少。

题解

一道很好的树形DP题目。首先的话,对于一个点要搞清楚寻找最长距离所能转移的三个状态。一种状态是沿着子节点DFS,寻找最长距离。第二种状态是,先向父节点走一步,然后沿着另一条线路DFS。第三种状态是,向父节点走多步。
针对这三种状态,可以使用一个二维DP数组对状态进行记录。使用dp[0][x]代表向下走的最长距离,用dp[1][x]代表向下走的次长距离,dp[2][x]代表向上走的最长距离。首先一遍DFS就可以求得dp[0][x],dp[1][x]。然后再来一遍DFS,求得dp[2][x]。dp[2][x]的计算也算是个小技巧吧,在父状态对子状态的dp[2][x]进行赋值,这样的话就可以保证子状态转移到父状态之后不会再转移回去。

注意事项

这道题最重要的是想法,没有什么坑。注意一下初始化就行了。

代码

#include <iostream>#include<cstdio>#include<algorithm>#include<cstring>#include<vector>#include<cmath>#include<queue>#include<string>#include<set>#include<map>#include<bitset>#include<stack>#define UP(i,l,h) for(int i=l;i<h;i++)#define DOWN(i,h,l) for(int i=h-1;i>=l;i--)#define W(a) while(a)#define MEM(a,b) memset(a,b,sizeof(a))#define INF 0x3f3f3f3f3f3f3f3f#define LL long long#define MAXN 10010#define SIZE 95#define EPS 1e-10#define MOD 1000000007using namespace std;struct Node {    int son,val;    Node(int son,int val):son(son),val(val) {}};vector<Node> nodes[MAXN];int p[MAXN],mxson[MAXN];int dp[3][MAXN];int dfs(int u) {    if(dp[0][u]>0)        return dp[0][u];    int sz=nodes[u].size();    UP(i,0,sz) {        Node son=nodes[u][i];        int d=dfs(son.son)+son.val;        if(d>dp[0][u]) {            dp[0][u]=d;            mxson[u]=son.son;        }    }    UP(i,0,sz) {        Node son=nodes[u][i];//        cout<<" xx"<<son.son<<" "<<u<<" "<<mxson[u]<<endl;        if(son.son==mxson[u]) {            continue;        }        int d=dp[0][son.son]+son.val;//        cout<<d<<endl;        if(d>dp[1][u]) {            dp[1][u]=d;        }    }    return dp[0][u];}void dfs2(int u) {    int sz=nodes[u].size();    UP(i,0,sz) {        Node son=nodes[u][i];//        cout<<"son"<<son.son<<" "<<dp[2][u]<<" "<<dp[1][u]<<endl;        if(son.son==mxson[u]) {            dp[2][son.son]=max(dp[2][u],dp[1][u])+son.val;        } else {            dp[2][son.son]=max(dp[2][u],dp[0][u])+son.val;        }        dfs2(son.son);    }}int main() {    int n;    W(~scanf("%d",&n)) {        MEM(dp,0);        MEM(mxson,0);        UP(i,1,n+1){            nodes[i].clear();        }        int pa,val;        UP(i,2,n+1) {            scanf("%d%d",&pa,&val);            p[i]=pa;            nodes[pa].push_back(Node(i,val));        }        dfs(1);        dfs2(1);        UP(i,1,n+1)            printf("%d\n",max(dp[0][i],dp[2][i]));    }}
原创粉丝点击