hdu2196Computer 经典树形dp 在树上求最长距离

系统 1851 0

hdu2196

题解

两次搜索的方法

 

    #include<iostream>

#include<cstdio>

#include<cstring>

#include<vector>

using namespace std;



int N,V[10100];						

vector<int>son[10100];				//图 

int MAX[10100],MAXN[10100];			//最大值及其标号 

int SMAX[10100],SMAXN[10100];		//次大值及其标号 

bool	vis[10100];					//标记访问状态  



void dfs1(int n)					//在以n为根节点的子树上求出节点n到叶子节点距离的最大值 

{

	MAX[n]=SMAX[n]=0;

	int len=son[n].size();

	for(int i=0;i<len;i++)

	{

		int k=son[n][i];	//儿子标号 - - 

		dfs1(k);

		if(SMAX[n]<MAX[k]+V[k])	

		{

			SMAX[n]=MAX[k]+V[k];

			SMAXN[n]=k;

			if(SMAX[n]>MAX[n]){

				swap(SMAX[n],MAX[n]);

				swap(SMAXN[n],MAXN[n]);

			}

		}

	}

}



void dfs2(int n)			//求出n的儿子们在树中能延伸的最大距离(n的最大距离及次大距离已得到) 

{

	int len=son[n].size();

	vis[n]=1;

	for(int i=0;i<len;i++)

	{

		int k=son[n][i];

		if(vis[k])	continue;

		if(k==MAXN[n]){

			

			if(SMAX[k]<SMAX[n]+V[k]){

				SMAX[k]=SMAX[n]+V[k];

				SMAXN[k]=n;

				if(SMAX[k]>MAX[k]){

					swap(SMAX[k],MAX[k]);

					swap(SMAXN[k],MAXN[k]);

				}

			}

		}

		else{

			

			if(SMAX[k]<MAX[n]+V[k]){

				SMAX[k]=MAX[n]+V[k];

				SMAXN[k]=n;

				if(SMAX[k]>MAX[k]){

					swap(SMAX[k],MAX[k]);

					swap(SMAXN[k],MAXN[k]);

				}

			}

		}

		dfs2(k);

	}

}







int main()

{

	int i,j,k,u,v;

	while(scanf("%d",&N)!=EOF)

	{

		for(i=1;i<=N;i++)	son[i].clear();

		for(i=2;i<=N;i++){

			scanf("%d%d",&u,&V[i]);

			son[u].push_back(i);					//i的父亲是u 

		}

		memset(vis,0,sizeof(vis));

		dfs1(1);

	//	测试 

	//	for(i=1;i<=N;i++)	printf("~%d ",MAX[i]);printf("\n");

	//	for(i=1;i<=N;i++)	printf("~%d ",SMAX[i]);printf("\n");

	

		memset(vis,0,sizeof(vis));

		dfs2(1);

		for(i=1;i<=N;i++)	printf("%d\n",MAX[i]);

	}

	return 0;

}

/*

5 

1 1 

2 1 

3 1 

1 1 

*/
  


 

 

hdu2196Computer 经典树形dp 在树上求最长距离


更多文章、技术交流、商务合作、联系博主

微信扫码或搜索:z360901061

微信扫一扫加我为好友

QQ号联系: 360901061

您的支持是博主写作最大的动力,如果您喜欢我的文章,感觉我的文章对您有帮助,请用微信扫描下面二维码支持博主2元、5元、10元、20元等您想捐的金额吧,狠狠点击下面给点支持吧,站长非常感激您!手机微信长按不能支付解决办法:请将微信支付二维码保存到相册,切换到微信,然后点击微信右上角扫一扫功能,选择支付二维码完成支付。

【本文对您有帮助就好】

您的支持是博主写作最大的动力,如果您喜欢我的文章,感觉我的文章对您有帮助,请用微信扫描上面二维码支持博主2元、5元、10元、自定义金额等您想捐的金额吧,站长会非常 感谢您的哦!!!

发表我的评论
最新评论 总共0条评论