HDU 2196 Computer(树形DP)
来源:互联网 发布:tensorflow 好玩 编辑:程序博客网 时间:2024/05/11 20:37
Description
求树中每个点到所有节点的距离的最大值是多少
Input
第一行一个整数表示节点数,之后n-1行每行两个整数a和b表示a和b有一条边
Output
按顺序输出每个点到其他点距离的最大值
Sample Input
5
1 1
2 1
3 1
1 1
Sample Output
3
2
3
4
4
Solution
树形dp,由于对于一个节点来说,可能得到的距离最大的值的路径来自他的子树,或者从他的父节点过来,所以用两次dfs。第一次dfs求出所有节点在他的子树范围内到叶子节点距离的最大值和第二大的值,第二次dfs更新从父节点过来的情况就可以了。因为如果只存最大值的话,判断一个点的从父节点过来的最大值,那么如果他的父节点存的最大值正好是从该点过来的,那么就失去了从父节点过来的状态,所以要记录最大的两个值
Code
#include<cstdio>#include<iostream>#include<algorithm>#include<cstring>using namespace std;const int Maxn=11111;struct node{ int to; int next; int len;}edge[Maxn*2];int head[Maxn];int tol;int maxn[Maxn];//每个点到其他点距离最大值 int smaxn[Maxn];//每个点到其他点距离次大值 int maxid[Maxn];//与该点距离最大的点的序号 int smaxid[Maxn];//与该点距离次大的点的序号 void init()//初始化 { tol=0; memset(head,-1,sizeof(head));}void add(int a,int b,int len)//建双向边 { edge[tol].to=b; edge[tol].len=len; edge[tol].next=head[a]; head[a]=tol++; edge[tol].to=a; edge[tol].len=len; edge[tol].next=head[b]; head[b]=tol++;}void dfs1(int u,int p){ maxn[u]=0; smaxn[u]=0; for(int i=head[u];i!=-1;i=edge[i].next) { int v=edge[i].to; if(v==p)continue; dfs1(v,u); if(smaxn[u]<maxn[v]+edge[i].len)//首先更新次大值 { smaxn[u]=maxn[v]+edge[i].len; smaxid[u]=v; if(smaxn[u]>maxn[u])//如果次大值比最大值大则将其互换即可 { swap(smaxn[u],maxn[u]); swap(smaxid[u],maxid[u]); } } }}void dfs2(int u,int p){ for(int i=head[u];i!=-1;i=edge[i].next) { int v=edge[i].to; if(v==p)continue; if(v==maxid[u])//如果该点父亲节点存的最大值正好从该点过来,则用其父亲节点的次大值更新 { if(edge[i].len+smaxn[u]>smaxn[v])//首先更新次大值 { smaxn[v]=edge[i].len+smaxn[u]; smaxid[v]=u; if(smaxn[v]>maxn[v])//如果次大值比最大值大则将其互换即可 { swap(smaxn[v],maxn[v]); swap(smaxid[v],maxid[v]); } } } else//如果该点父亲节点存的最大值正好从该点过来,则用其父亲节点的最大值更新 { if(edge[i].len+maxn[u]>smaxn[v])//首先更新次大值 { smaxn[v]=edge[i].len+maxn[u]; smaxid[v]=u; if(smaxn[v]>maxn[v])//如果次大值比最大值大则将其互换即可 { swap(smaxn[v],maxn[v]); swap(maxid[v],smaxid[v]); } } } dfs2(v,u); }}int main(){ int n; int v,len; while(scanf("%d",&n)!=EOF) { init(); for(int i=2;i<=n;i++) { scanf("%d%d",&v,&len); add(i,v,len); } dfs1(1,-1);//第一次dfs求出所有节点在他的子树范围内到叶子节点距离的最大值和第二大的值 dfs2(1,-1);//第二次dfs更新从父节点过来的情况 for(int i=1;i<=n;i++) printf("%d\n",maxn[i]); } return 0;}
0 0
- hdu 2196 Computer(DP-树形DP)
- HDU 2196--Computer(树形dp)
- hdu 2196 computer (树形dp)
- HDU 2196 Computer(树形dp经典)
- HDU 2196 Computer(经典树形DP)
- HDU 2196 Computer(树形dp)
- hdu 2196 Computer(树形DP)
- hdu 2196 Computer(经典树形DP)
- HDU 2196 Computer(树形DP)
- hdu 2196 computer(树形dp)
- HDU 2196 Computer(树形dp经典)
- HDU 2196 Computer(树形DP)
- HDU 2196 Computer (树形DP)
- [HDU 2196] Computer (树形dp)
- hdu 2196 Computer (树形DP)
- 【hdu 2196】Computer(树形dp)
- hdu 2196 Computer(树形DP)
- hdu 2196(Computer 树形dp)
- centOS 7.1.1503 搭建vsftpd环境-使用虚拟用户登录
- android APP常用的颜色及代码
- 23种设计模式全解析
- 天声人語 20150807
- Linux系统挂载U盘
- HDU 2196 Computer(树形DP)
- 【MST+虚拟节点+Kruskal】swjtuOJ 2093
- 日经春秋 20150807
- UML建模学习(一)
- h5视频播放
- jQuery数据类型总结
- 对牛顿方法的一点理解
- 吐槽一下Hibernate
- 网络端口被占用情况查看