POJ 1986 Distance Queries(Tarjan离线法求LCA)
| Time Limit: 2000MS | Memory Limit: 30000K | |
| Total Submissions: 12846 | Accepted: 4552 | |
| Case Time Limit: 1000MS | ||
Description
Input
* 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
Sample Input
7 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 Output
13
3
36
Hint
题目连接:POJ 1986
简单模版题,一棵树中两点的距离$d(u,v)$可以用$d[u]+d[v]-2*d[lca(u,v)]$来求得,其中$d_i$是你设定的根到某一点$i$的距离,那显然首先随便找个点进行最短路或者直接DFS获得d数组,再Tarjan得出答案
代码:
#include <stdio.h>
#include <iostream>
#include <algorithm>
#include <cstdlib>
#include <sstream>
#include <cstring>
#include <bitset>
#include <string>
#include <deque>
#include <stack>
#include <cmath>
#include <queue>
#include <set>
#include <map>
using namespace std;
#define INF 0x3f3f3f3f
#define CLR(arr,val) memset(arr,val,sizeof(arr))
#define LC(x) (x<<1)
#define RC(x) ((x<<1)+1)
#define MID(x,y) ((x+y)>>1)
typedef pair<int,int> pii;
typedef long long LL;
const double PI=acos(-1.0);
const int N=40010;
struct edge
{
int to;
int nxt;
int w;
};
struct query
{
int to;
int nxt;
int id;
}; edge E[N<<1];
query Q[N<<1];
int head[N],rhead[N],tot,rtot;
int d[N],dx[N],vis[N],in[N];
int pre[N],ances[N]; void init()
{
CLR(head,-1);
CLR(rhead,-1);
tot=rtot=0;
CLR(d,0);
for (int i=0; i<N; ++i)
{
pre[i]=i;
ances[i]=0;
}
CLR(vis,0);
CLR(in,0);
CLR(dx,0);
}
int Find(int n)
{
if(pre[n]==n)
return n;
return pre[n]=Find(pre[n]);
}
inline void add(int s,int t,int d)
{
E[tot].to=t;
E[tot].w=d;
E[tot].nxt=head[s];
head[s]=tot++;
}
inline void addquery(int s,int t,int id)
{
Q[rtot].id=id;
Q[rtot].to=t;
Q[rtot].nxt=rhead[s];
rhead[s]=rtot++;
}
void LCA(int u)
{
vis[u]=1;
ances[u]=u;
int i,v;
for (i=head[u]; ~i; i = E[i].nxt)
{
v = E[i].to;
if(!vis[v])
{
LCA(v);
pre[v]=u;
ances[Find(u)]=u;
}
}
for (i=rhead[u]; ~i; i = Q[i].nxt)
{
v=Q[i].to;
if(vis[v])
dx[Q[i].id]=d[u]+d[v]-(d[ances[Find(v)]]<<1);
}
}
void dfs(int u,int fa,int sum)
{
d[u]=sum;
for (int i=head[u]; ~i; i = E[i].nxt)
{
int v=E[i].to;
if(v!=fa)
dfs(v,u,sum+E[i].w);
}
}
int main(void)
{
int n,m,a,b,c,i,k;
char nouse[5];
while (~scanf("%d%d",&n,&m))
{
init();
for (i=0; i<m; ++i)
{
scanf("%d%d%d%s",&a,&b,&c,nouse);
add(a,b,c);
add(b,a,c);
++in[b];
}
scanf("%d",&k);
for (i=0; i<k; ++i)
{
scanf("%d%d",&a,&b);
addquery(a,b,i);
addquery(b,a,i);
}
for (i=1; i<=n; ++i)
{
if(!in[i])
{
dfs(i,-1,0);
LCA(i);
break;
}
}
for (i=0; i<k; ++i)
printf("%d\n",dx[i]);
}
return 0;
}
POJ 1986 Distance Queries(Tarjan离线法求LCA)的更多相关文章
- POJ - 1986 Distance Queries(离线Tarjan算法)
1.一颗树中,给出a,b,求最近的距离.(我没考虑不联通的情况,即不是一颗树的情况) 2.用最近公共祖先来求, 记下根结点到任意一点的距离dis[],这样ans = dis[u] + dis[v] - ...
- POJ 1986 Distance Queries / UESTC 256 Distance Queries / CJOJ 1129 【USACO】距离咨询(最近公共祖先)
POJ 1986 Distance Queries / UESTC 256 Distance Queries / CJOJ 1129 [USACO]距离咨询(最近公共祖先) Description F ...
- POJ.1986 Distance Queries ( LCA 倍增 )
POJ.1986 Distance Queries ( LCA 倍增 ) 题意分析 给出一个N个点,M条边的信息(u,v,w),表示树上u-v有一条边,边权为w,接下来有k个询问,每个询问为(a,b) ...
- POJ 1986 Distance Queries LCA两点距离树
标题来源:POJ 1986 Distance Queries 意甲冠军:给你一棵树 q第二次查询 每次你问两个点之间的距离 思路:对于2点 u v dis(u,v) = dis(root,u) + d ...
- POJ 1986 Distance Queries 【输入YY && LCA(Tarjan离线)】
任意门:http://poj.org/problem?id=1986 Distance Queries Time Limit: 2000MS Memory Limit: 30000K Total ...
- POJ 1986 Distance Queries(LCA Tarjan法)
Distance Queries [题目链接]Distance Queries [题目类型]LCA Tarjan法 &题意: 输入n和m,表示n个点m条边,下面m行是边的信息,两端点和权,后面 ...
- POJ 1986 Distance Queries (Tarjan算法求最近公共祖先)
题目链接 Description Farmer John's cows refused to run in his marathon since he chose a path much too lo ...
- POJ 1986 Distance Queries (最近公共祖先,tarjan)
本题目输入格式同1984,这里的数据范围坑死我了!!!1984上的题目说边数m的范围40000,因为双向边,我开了80000+的大小,却RE.后来果断尝试下开了400000的大小,AC.题意:给出n个 ...
- poj 1986 Distance Queries LCA
题目链接:http://poj.org/problem?id=1986 Farmer John's cows refused to run in his marathon since he chose ...
随机推荐
- ember.js:使用笔记1-数组数据统一显示
ember中数据一般都是以array的形式存储的,控制器使用,如: App.DataController = Em.ArrayController.extend({}); 想要在一个页面中输出所有的数 ...
- Mvc网站发布到IIS
网站发布步骤: 这部分是转载文章 在此标明出处,以前有文章是转的没标明的请谅解,因为有些已经无法找到出处,或者与其它原因. 如有冒犯请联系本人,或删除,或标明出处. 因为好的文章,以前只想收藏,但连接 ...
- WPF画线问题,几千条以后就有明显的延迟了。
我现在是这么画的,class A { private GeometryGroup _lines; private Path _path; public A() { _path.Data = ...
- Excel: Switch (transpose) columns and rows
链接:https://support.office.com/en-in/article/Switch-transpose-columns-and-rows-ed1215f5-59af-47e6-953 ...
- 创建第一个Hiberntae工程
一.前言 很久之前已经对Hibernate有所了解,在项目中进行过简单的应用,基本了解hibernate的简单应用,没有深入的了解,来Shine公司快三个月了,公司的ORM框架就是用Hiberante ...
- CSS雪碧,即CSS Sprite 简单的例子
CSS Sprite生成工具 http://pan.baidu.com/s/1gdGQwiJ 工具可将多幅图片整合一张,并生成CSS. HTML代码 <style> .img{backgr ...
- 【ZOJ】1015 Fishing Net
http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=1015 题意:给出一个n个点的无向图,询问是否为弦图,弦图定义为对于图中任意 ...
- 【JAVA基础】 MAP 遍历
public static void main(String[] args) { Map<String, String> map = new HashMap<String, Stri ...
- thinkphp 联表查询,排序
$info =M('productbase'); $info= $info->alias('a')->field('a.id,cid,title,address,protype,time, ...
- PHP面向对象学习一
1. 抽象性 , 2. 封装性 ,3.共享性 ,4. 强调对象结构而不是程序结构 面向对象的三大特点(封装,继承,多态)缺一不可 class MyPc{ ———创建一个名为 MyPc的类,class ...