题意:
给出一棵树..求出一条路..使得别的点到这条路径的距离最长的最短..
输入:
n 表示树上有n个点..
u v w 表示u和v这两个相连的点的边权值为w
思路:
3次广搜..
第一次从任意一个点找最长的路径~这个路径的终点就是要求的路的终点..
第二次从终点开始找最长的路径..这时候找到的路径就是最后的路了..
然后从这个队列往外遍历相连的路..
这时候找出来的最长的距离就是要求的答案..
Tips:
因为加边的时候是双向边..
所以边的数组应该开两倍大..
pre 数组要注意~~~~
Code:
1 #include <iostream> 2 #include <cstring> 3 #include <stdio.h> 4 using namespace std; 5 #define clr(x) memset(x, 0, sizeof(x)) 6 7 const int MAXN = 100010; 8 9 struct Edge 10 { 11 int to; 12 int next; 13 int w; 14 }edge[MAXN*2]; 15 int tot; 16 int head[MAXN]; 17 18 void add(int s, int u, int w) { 19 edge[tot].to = u; 20 edge[tot].next = head[s]; 21 edge[tot].w = w; 22 head[s] = tot++; 23 24 edge[tot].to = s; 25 edge[tot].next = head[u]; 26 edge[tot].w = w; 27 head[u] = tot++; 28 } 29 30 struct Node 31 { 32 int num; 33 int dis; 34 }que[MAXN]; 35 36 bool vis[MAXN]; 37 int rd[MAXN]; 38 int bfs() 39 { 40 Node tmp, tmp1; 41 int pre[MAXN]; 42 int tmps, ma = 0, s, e, ans = 0; 43 clr(pre); 44 int front = 0, rear = 0; 45 clr(vis); 46 tmp.num = 1; 47 tmp.dis = 0; 48 que[rear++] = tmp; 49 vis[1] = true; 50 while(front < rear) { 51 tmp = que[front++]; 52 tmps = tmp.num; 53 for(int i = head[tmps]; i; i = edge[i].next) 54 if(!vis[edge[i].to]) { 55 tmp1.num = edge[i].to; 56 tmp1.dis = edge[i].w + tmp.dis; 57 que[rear++] = tmp1; 58 vis[edge[i].to] = true; 59 if(ma < tmp1.dis) { 60 ma = tmp1.dis; 61 e = tmp1.num; 62 } 63 } 64 } 65 66 ma = front = rear = 0; 67 clr(vis); 68 tmp.num = e; 69 tmp.dis = 0; 70 que[rear++] = tmp; 71 vis[e] = true; 72 while(front < rear) { 73 tmp = que[front++]; 74 tmps = tmp.num; 75 for(int i = head[tmps]; i; i = edge[i].next) 76 if(!vis[edge[i].to]) { 77 tmp1.num = edge[i].to; 78 tmp1.dis = edge[i].w + tmp.dis; 79 vis[edge[i].to] = true; 80 que[rear++] = tmp1; 81 pre[tmp1.num] = tmps; 82 if(ma < tmp1.dis) { 83 s = tmp1.num; 84 ma = tmp1.dis; 85 } 86 } 87 } 88 89 ma = front = rear = 0; 90 clr(vis); 91 tmp.num = s; 92 tmp.dis = 0; 93 que[rear++] = tmp; 94 //printf("%d===>", s); 95 while(pre[s]) { 96 //printf("%d==>", pre[s]); 97 tmp.num = pre[s]; 98 tmp.dis = 0; 99 que[rear++] = tmp; 100 vis[s] = true; 101 s = pre[s]; 102 } 103 //printf("%d", e); 104 //puts(""); 105 vis[e] = true; 106 while(front < rear) { 107 tmp = que[front++]; 108 tmps = tmp.num; 109 for(int i = head[tmps]; i; i = edge[i].next) 110 if(!vis[edge[i].to]) { 111 tmp1.num = edge[i].to; 112 tmp1.dis = edge[i].w + tmp.dis; 113 que[rear++] = tmp1; 114 vis[tmp1.num] = true; 115 if(tmp1.dis > ma) { 116 ma = tmp1.dis; 117 } 118 } 119 } 120 return ma; 121 } 122 123 124 int main() 125 { 126 int i, j, k; 127 int n, a, b; 128 int u, v, w; 129 while(scanf("%d", &n) != EOF) { 130 if(n == 0) break; 131 132 tot = 1; 133 clr(head); 134 for(i = 0; i < n-1; ++i) { 135 scanf("%d %d %d", &u, &v, &w); 136 add(u, v, w); 137 } 138 139 printf("%d\n", bfs()); 140 } 141 return 0; 142 }
题目链接:http://acm.hrbust.edu.cn/index.php?m=ProblemSet&a=showProblem&problem_id=1460