hdu 3534 树形dp

题意:给定一棵树,求出树的直径以及个数。

思路:dfs到结点u时,顺便统计出以u为lca的路径的最长距离和个数。故需要求出每个结点到叶子结点的最长距离以及个数。题目居然不给数据范围,不过实测n最大值为10000。

 1 #include <iostream>
 2 #include <cstring>
 3 #include <cstdio>
 4 using namespace std;
 5 
 6 const int N = 10001;
 7 int head[N];
 8 int len[N];
 9 int num[N];
10 int n, e, ans, cnt;
11 
12 void init()
13 {
14     e = 0;
15     ans = 0;
16     cnt = 1;
17     memset( head, -1, sizeof(head) );
18 }
19 
20 struct Edge 
21 {
22     int v, next, w;
23 } edge[N << 1];
24 
25 void addEdge( int u, int v, int w )
26 {
27     edge[e].v = v;
28     edge[e].w = w;
29     edge[e].next = head[u];
30     head[u] = e++;
31 }
32 
33 void dfs( int u, int fa )
34 {
35     len[u] = 0;
36     num[u] = 1;
37     for ( int i = head[u]; i != -1; i = edge[i].next )
38     {
39         int v = edge[i].v, w = edge[i].w;
40         if ( v == fa ) continue;
41         dfs( v, u );
42         if ( len[u] + len[v] + w > ans )
43         {
44             ans = len[u] + len[v] + w;
45             cnt = num[u] * num[v];
46         }
47         else if ( len[u] + len[v] + w == ans )
48         {
49             cnt += num[u] * num[v];
50         }
51         if ( len[v] + w > len[u] )
52         {
53             len[u] = len[v] + w;
54             num[u] = num[v];
55         }      
56         else if ( len[v] + w == len[u] )
57         {
58             num[u] += num[v];
59         }
60     }
61 }
62 
63 int main ()
64 {
65     while ( scanf("%d", &n) != EOF )
66     {
67         init();
68         for ( int i = 1; i < n; i++ )
69         {
70             int u, v, w;
71             scanf("%d%d%d", &u, &v, &w);
72             addEdge( u, v, w );
73             addEdge( v, u, w );
74         }
75         dfs( 1, -1 );
76         printf("%d %d\n", ans, cnt);
77     }
78     return 0;
79 }

 

posted @ 2015-08-21 12:55  hxy_has_been_used  阅读(112)  评论(0编辑  收藏  举报