BZOJ 3362 Navigation Nightmare

一道带权并查集题目.

带权并查集的重点是信息的合并.

这类题出现得并不多,练习一下.

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define ll long long
 4 #define FILE "dealing"
 5 #define up(i,j,n) for(int i=j;i<=n;i++)
 6 #define db long double 
 7 #define pii pair<int,int>
 8 #define pb push_back
 9 #define mem(a,L) memset(a,0,sizeof(int)*(L+1))
10 template<class T> inline bool cmin(T& a,T b){return a>b?a=b,true:false;}
11 template<class T> inline bool cmax(T& a,T b){return a<b?a=b,true:false;}
12 template<class T> inline T squ(T a){return a*a;}
13 const ll maxn=210000+10,inf=1e9+10,mod=10000007,M=9988440;
14 ll read(){
15     ll x=0,f=1,ch=getchar();
16     while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
17     while(ch>='0'&&ch<='9')x=(x<<1)+(x<<3)+ch-'0',ch=getchar();
18     return x*f;
19 }
20 int l[maxn],r[maxn],fa[maxn];
21 int getfa(int x){
22     if(fa[x]==x)return x;
23     int y=getfa(fa[x]);
24     if(y==fa[x])return y;
25     l[x]+=l[fa[x]],r[x]+=r[fa[x]];
26     fa[x]=y;
27     return y;
28 }
29 int n,m,Q;
30 int f1[maxn],f2[maxn],d[maxn],op[maxn];
31 int xx[maxn],yy[maxn],t[maxn],ans[maxn];
32 vector<int> linkk[maxn];
33 int main(){
34     freopen(FILE".in","r",stdin);
35     freopen(FILE".out","w",stdout);
36     n=read(),m=read();
37     char ch;
38     up(i,1,m){
39         f1[i]=read(),f2[i]=read(),d[i]=read();
40         scanf(" %c",&ch);
41         if(ch=='E')op[i]=1;
42         else if(ch=='W')op[i]=2;
43         else if(ch=='N')op[i]=3;
44         else if(ch=='S')op[i]=4;
45     }
46     Q=read();
47     up(i,1,Q){
48         xx[i]=read(),yy[i]=read(),t[i]=read();
49         linkk[t[i]].push_back(i);
50     }
51     up(i,1,n)fa[i]=i;
52     up(i,1,m){
53         int x=f1[i],y=f2[i],fx=getfa(x),fy=getfa(y);
54         if(fx!=fy){
55             if(fx!=x)l[fx]=-l[x],r[fx]=-r[x],l[x]=r[x]=0,fa[fx]=x,fa[x]=x;
56             if(fy!=y)l[fy]=-l[y],r[fy]=-r[y],l[y]=r[y]=0,fa[fy]=y,fa[y]=y;
57             fa[x]=y;
58             if(op[i]==1)l[x]=d[i];
59             else if(op[i]==2)l[x]=-d[i];
60             else if(op[i]==3)r[x]=d[i];
61             else r[x]=-d[i];
62         }
63         for(int j=0;j<linkk[i].size();j++){
64             int t=linkk[i][j];
65             int x=xx[t],y=yy[t];
66             int fx=getfa(x),fy=getfa(y);
67             if(fx!=fy)ans[t]=-1;
68             else ans[t]=abs(l[x]-l[y])+abs(r[x]-r[y]);
69         }
70     }
71     up(i,1,Q)printf("%d\n",ans[i]);
72     return 0;
73 }
View Code

 

posted @ 2017-05-04 09:32  CHADLZX  阅读(119)  评论(0编辑  收藏  举报