hdu 4607 Park Visit(树上最长链)

求树上最长链:两遍搜索。

第一次从树上任意点开始,最远点必然是某一条最长链上的端点u。

第二次从u开始,最远点即该最长链的另一端点。

先在最长链上走,不足再去走支链。

把询问数m错打成n,狠狠wa了一次= =

 1 #include<stdio.h>
 2 #include<string.h>
 3 
 4 const int MAXN=111111;
 5 
 6 struct E{
 7     int v,next;
 8 }e[MAXN<<1];
 9 
10 struct Q{
11     int p,c;
12 }q[MAXN];
13 
14 int tol;
15 int head[MAXN];
16 int vis[MAXN];
17 
18 void init()
19 {
20     tol=0;
21     memset(head,-1,sizeof(head));
22 }
23 
24 void add(int u,int v)
25 {
26     e[tol].v=v;
27     e[tol].next=head[u];
28     head[u]=tol++;
29 }
30 
31 int BFS(int x)
32 {
33     int r,l,i;
34     int u,c;
35     r=l=0;
36     memset(vis,0,sizeof(vis));
37     vis[x]=1;
38     q[r].p=x;
39     q[r++].c=1;
40     while(l<r)
41     {
42         u=q[l].p;
43         c=q[l++].c;
44         for(i=head[u];i!=-1;i=e[i].next)
45         {
46             int v=e[i].v;
47             if(!vis[v]){
48                 vis[v]=1;
49                 q[r].p=v;
50                 q[r++].c=c+1;
51             }
52         }
53     }
54     return u;
55 }
56 
57 int main()
58 {
59     int T,n,m,i;
60     int u,v,w;
61     scanf("%d",&T);
62     while(T--)
63     {
64         scanf("%d%d",&n,&m);
65         init();
66         for(i=1;i<n;i++)
67         {
68             scanf("%d%d",&u,&v);
69             add(u,v);
70             add(v,u);
71         }
72         u=BFS(1);
73         v=BFS(u);
74         for(i=0;i<m;i++)
75         {
76             scanf("%d",&w);
77             if(q[n-1].c>=w)
78                 printf("%d
",w-1);
79             else
80                 printf("%d
",(q[n-1].c-1)+(w-q[n-1].c)*2);
81         }
82     }
83     return 0;
84 }
View Code
原文地址:https://www.cnblogs.com/zstu-abc/p/3220764.html