hdoj_2586How far away ? && poj_1986Distance Queries
2013-06-02 22:49
417 查看
How far away ?
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 2931 Accepted Submission(s): 1092
Problem Description
There are n houses in the village and some bidirectional roads connecting them. Every day peole always like to ask like this "How far is it if I want to go from house A to house B"? Usually it hard to answer. But luckily int this village the answer is always
unique, since the roads are built in the way that there is a unique simple path("simple" means you can't visit a place twice) between every two houses. Yout task is to answer all these curious people.
Input
First line is a single integer T(T<=10), indicating the number of test cases.
For each test case,in the first line there are two numbers n(2<=n<=40000) and m (1<=m<=200),the number of houses and the number of queries. The following n-1 lines each consisting three numbers i,j,k, separated bu a single space, meaning that there is a road
connecting house i and house j,with length k(0<k<=40000).The houses are labeled from 1 to n.
Next m lines each has distinct integers i and j, you areato answer the distance between house i and house j.
Output
For each test case,output m lines. Each line represents the answer of the query. Output a bland line after each test case.
Sample Input
2
3 2
1 2 10
3 1 15
1 2
2 3
2 2
1 2 100
1 2
2 1
Sample Output
10
25
100100
#include <iostream> #include <cstdio> #include <cstring> using namespace std; #pragma warning(disable : 4996) const int MAXN = 40002; typedef struct Edge { int v; int w; int next; }Edge; int cnt, edge_head[MAXN], ask_head[MAXN]; int father[MAXN], dist[MAXN], ans[201]; bool visited[MAXN]; Edge edge[2 * MAXN], ask[404]; int find(int x) { if (x != father[x]) { father[x] = find(father[x]); } return father[x]; } void add_edge(int x, int y, int z) { edge[cnt].v = y; edge[cnt].w = z; edge[cnt].next = edge_head[x]; edge_head[x] = cnt++; } void add_ask(int x, int y, int cast) { ask[cnt].v = y; ask[cnt].w = cast; ask[cnt].next = ask_head[x]; ask_head[x] = cnt++; } void Tarjan(int k) { visited[k] = true; for (int i = ask_head[k]; i != 0; i = ask[i].next) { if (visited[ask[i].v]) { ans[ask[i].w] = dist[ask[i].v] + dist[k] - 2 * dist[find(ask[i].v)]; } } for (int i = edge_head[k]; i != 0; i = edge[i].next) { if (!visited[edge[i].v]) { dist[edge[i].v] = dist[k] + edge[i].w; Tarjan(edge[i].v); edge[i].v = find(edge[i].v); father[edge[i].v] = k; } } } int main() { freopen("in.txt", "r", stdin); int i, m, n; int x, y, z; int t; scanf("%d", &t); while (t--) { scanf("%d %d", &n, &m); for (i = 1; i <= n; i++) { edge_head[i] = ask_head[i] = 0; father[i] = i; visited[i] = false; } cnt = 1; for (i = 1; i < n; i++) { scanf("%d%d%d", &x, &y, &z); add_edge(x, y, z); add_edge(y, x, z); } cnt = 1; for (i = 1; i <= m; i++) { scanf("%d%d", &x, &y); add_ask(x, y, i); add_ask(y, x, i); } dist[1] = 0; Tarjan(1); for (i = 1; i <= m; i++) printf("%d\n", ans[i]); } return 0; }
Distance Queries
Time Limit: 2000MS | Memory Limit: 30000K | |
Total Submissions: 7456 | Accepted: 2619 | |
Case Time Limit: 1000MS |
Input* Lines 1..1+M: Same format as "Navigation Nightmare"
* Line 2+M: A single integer, K. 1 <= K <= 10,000
* Lines 3+M..2+M+K: Each line corresponds to a distance query and contains the indices of two farms.
Output* Lines 1..K: For each distance query, output on a single line an integer giving the appropriate distance.
Sample Input7 6
1 6 13 E
6 3 9 E
3 5 7 S
4 1 3 N
2 4 20 W
4 7 2 S
3
1 6
1 4
2 6
Sample Output13
3
36
#include <iostream> #include <cstdio> #include <cstring> using namespace std; #pragma warning(disable : 4996) const int MAXN = 10000005; typedef struct Edge { int v; int w; int next; }Edge; int cnt, edge_head[MAXN], ask_head[MAXN]; int father[MAXN], dist[MAXN], ans[MAXN]; bool visited[MAXN]; Edge edge[2 * MAXN], ask[MAXN]; int find(int x) { if (x != father[x]) { father[x] = find(father[x]); } return father[x]; } void add_edge(int x, int y, int z) { edge[cnt].v = y; edge[cnt].w = z; edge[cnt].next = edge_head[x]; edge_head[x] = cnt++; } void add_ask(int x, int y, int cast) { ask[cnt].v = y; ask[cnt].w = cast; ask[cnt].next = ask_head[x]; ask_head[x] = cnt++; } void Tarjan(int k) { visited[k] = true; for (int i = ask_head[k]; i != 0; i = ask[i].next) { if (visited[ask[i].v]) { ans[ask[i].w] = dist[ask[i].v] + dist[k] - 2 * dist[find(ask[i].v)]; } } for (int i = edge_head[k]; i != 0; i = edge[i].next) { if (!visited[edge[i].v]) { dist[edge[i].v] = dist[k] + edge[i].w; Tarjan(edge[i].v); edge[i].v = find(edge[i].v); father[edge[i].v] = k; } } } int main() { freopen("in.txt", "r", stdin); int i, m, n; int x, y, z; int q; scanf("%d %d", &n, &m); for (i = 1; i <= n; i++) { edge_head[i] = ask_head[i] = 0; father[i] = i; visited[i] = false; } cnt = 1; for (i = 1; i <= m; i++) { scanf("%d %d %d %*c", &x, &y, &z); add_edge(x, y, z); add_edge(y, x, z); } scanf("%d", &q); cnt = 1; for (i = 1; i <= q; i++) { scanf("%d%d", &x, &y); add_ask(x, y, i); add_ask(y, x, i); } dist[1] = 0; Tarjan(1); for (i = 1; i <= q; i++) printf("%d\n", ans[i]); return 0; }
相关文章推荐
- hdoj_2586How far away ? && poj_1986Distance Queries
- POJ 1986 Distance Queries && HDOJ 2586 How far away?
- poj 1986 RMQ&&LCA( 模板题)
- hdoj 1454&&poj 1039 Pipe 1454 (数学计算几何) 枚举
- hdoj Pipe&&南阳oj管道问题&&poj1039(计算几何问题...枚举)
- hdoj_1102Constructing Roads(最小生成树)&& poj_2485Highways
- 【线段树+扫描线】 HDOJ 1828 && POJ 1177 Picture
- HDOJ 1063 && POJ 1001
- HDOJ 1059 && POJ 1014 Dividing
- 【后缀数组】 HDOJ 2459 && POJ 3693 Maximum repetition substring
- poj 1422&&hdoj 1151 Air Raid
- hdoj 1969 (poj 3122&&acm)Pie
- poj 1006 && hdoj 1370 Biorhythms 【CRT】
- POJ 1631 / HDU 1950 / ZOJ 1986 / Northwestern Europe 2003 Bridging signals (DP&LIS)
- hdoj_1102Constructing Roads(最小生成树)&& poj_2485Highways
- POJ 3728 && POJ 1986
- HDOJ 1540 && POJ 2892 —— 线段树
- POJ-1308 & HDOJ-1325 Is It A Tree? 解题报告
- POJ 2062 & HDOJ 1528 Card Game Cheater - 阅读理解..二分图最大匹配
- poj_1579 && hdoj_1331