#1224 : 赛车
-
5 1 2 2 3 1 4 4 5
样例输出
-
4
描述
幻想乡有一个赛车场。赛车场里有N个地点。同时地点之间还有单向的道路存在。
这些道路使得赛车场形成了一个外向树的结构。也就是说,道路将这N个地点连成了一个有根树。并且所有的边都是从父亲指向孩子的。
由于幽香喜欢刺激,每次她去赛车场都会从根节点出发,选择最长的一条路径来玩。
但是现在幽香感觉最长的路径还是太短了,她打算在赛车场里新建一条道路使得新的最长路径最长。
同时,如果道路形成了一个环,那么可能会出现交通事故,所以幽香新建的道路不能导致环的出现。
你能帮幽香算出新建一条道路后的最长路径吗?幽香知道根节点一定是1号点。
输入
一行一个数N,表示地点的数量。
接下来N-1行,每行两个数a和b,表示从点a到点b有一条单向路径。所有点从1到n标号。
数据范围:
n<=100000。
输出
一行表示新建一条边后的最长路径。
解析:题解(by:陈立杰):http://media.hihocoder.com/contests/challenge14/hihoCoder-Challenge14-Solution.pdf
分析题意,我们可以知道,答案为这样的一种形式:
->x.....
路径:1->...->r
->y......
其中 x 为以 r 为根的子树中,最长的路径上的节点数,y为第二长的路径伤的节点数,1 到 r 之间有step-1个点(不含 1 与 r),答案即为:(x-1)+(y-1) +1 +1 +step
下附两组数据的图片:
代码:
#include<cstdio>
#include<algorithm>
#include<iostream>
using namespace std;
const int maxn=1e5;
struct tnode{int d,next;}q[maxn+20];
int n,h[maxn+20],ans=0;
int dfs(int r,int step)
{
int i,j,k=h[r],x=0,y=0;
while(k!=0)
{
j=dfs(q[k].d,step+1),k=q[k].next;
if(j>x)y=x,x=j;
else if(j>y)y=j;
}
ans=max(ans,x+y+step);
return x+1;
}
int main()
{
scanf("%d",&n);
int i,x,y;
for(i=1;i<n;i++)
{
scanf("%d%d",&x,&y);
q[i].d=y,q[i].next=h[x],h[x]=i;
}
dfs(1,0);
printf("%d\n",ans);
return 0;
}