首页 > 代码库 > 【poj1984】 Navigation Nightmare
【poj1984】 Navigation Nightmare
http://poj.org/problem?id=1984 (题目链接)
题意
给出一棵树,这棵树是以平面直角坐标系为基准建立的,也就是每个节点最多只有上下左右4条边。现在动态建树,同时询问两点间的曼哈顿距离
Solution
一开始没看懂题,当做图写了个SPFA。。后来发现是树于是删掉重新写了个DFS。。最后又发现要动态建树。。尼玛。。又重新写了个带全并查集。。
注意询问并不保证时间是升序的,要按照给定询问顺序输出。
代码
// poj1984#include<algorithm>#include<iostream>#include<cstdlib>#include<cstring>#include<cstdio>#include<cmath>#define LL long long#define MOD 100000000#define inf 2147483640#define Pi acos(-1.0)#define free(a) freopen(a".in","r",stdin),freopen(a".out","w",stdout);using namespace std;const int maxn=100010;struct edge {int u,v,w,t;}e[maxn];struct data {int u,v,id,d;}t[maxn];int n,m,q,X[maxn],Y[maxn],ans[maxn],fa[maxn];bool cmp(data a,data b) { return a.id<b.id;}int find(int x) { if (x==fa[x]) return x; int f=find(fa[x]); X[x]+=X[fa[x]]; Y[x]+=Y[fa[x]]; return fa[x]=f;}int main() { scanf("%d%d",&n,&m); char ch; for (int x,u,v,w,i=1;i<=m;i++) { scanf("%d%d%d %c",&u,&v,&w,&ch); if (ch==‘N‘) x=0;else if (ch==‘S‘) x=1;else if (ch==‘W‘) x=2;else x=3; e[i]=(edge){u,v,w,x}; } scanf("%d",&q); for (int i=1;i<=q;i++) scanf("%d%d%d",&t[i].u,&t[i].v,&t[i].id),t[i].d=i; sort(t+1,t+1+q,cmp); for (int i=1;i<=n;i++) fa[i]=i; int pp=1; for (int u,v,w,ty,i=1;i<=m;i++) { u=e[i].u,v=e[i].v,w=e[i].w,ty=e[i].t; int r1=find(u),r2=find(v); fa[r1]=v; if (ty==0) X[r1]-=X[u],Y[r1]=e[i].w-Y[u]; else if (ty==1) X[r1]-=X[u],Y[r1]=-e[i].w-Y[u]; else if (ty==2) X[r1]=-e[i].w-X[u],Y[r1]-=Y[u]; else X[r1]=e[i].w-X[u],Y[r1]-=Y[u]; while (t[pp].id==i && pp<=q) { if (find(t[pp].u)!=find(t[pp].v)) ans[t[pp].d]=-1; else ans[t[pp].d]=abs(X[t[pp].u]-X[t[pp].v])+abs(Y[t[pp].u]-Y[t[pp].v]); pp++; } if (pp==q+1) break; } for (int i=1;i<=q;i++) printf("%d\n",ans[i]); return 0;}
【poj1984】 Navigation Nightmare
声明:以上内容来自用户投稿及互联网公开渠道收集整理发布,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任,若内容有误或涉及侵权可进行投诉: 投诉/举报 工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。