标签:并查集
10 10 1 2 150 3 4 200 1 5 270 2 6 200 6 5 80 4 7 150 8 9 100 4 8 50 1 7 100 9 2 100
2HintHint:(PS: the 5th and 10th requests are incorrect)
这题可以用并查集做,属于带权值的并查集。t1,t2是根节点,其中root[t2]=root[a]+c-root[b];(可以用向量推)t2是集合二的根节点,a,b是输入的点
这里抄附上一张图
root[a]
a--------ra
| -
|x -
| root[b] -
b--------------------rb
原本以为rb经过集合合并后根节点是a,但其实是ra,所以可以递归并查集算出每个节点离根节点的距离
#include<iostream> #include<stdio.h> #include<string.h> #include<math.h> #include<algorithm> #include<map> #include<string> using namespace std; int pre[50005],root[50005]; int find(int x) { int temp; if(x==pre[x])return x; temp=pre[x]; pre[x]=find(pre[x]); root[x]=root[x]+root[temp]; return pre[x]; } int main() { int n,m,i,j,a,b,c,t1,t2,ans; while(scanf("%d%d",&n,&m)!=EOF) { for(i=0;i<=n;i++){ pre[i]=i;root[i]=0; } ans=0; for(i=1;i<=m;i++){ scanf("%d%d%d",&a,&b,&c); t1=find(a);t2=find(b); if(t1==t2){ if(root[b]-root[a]!=c){ ans++;continue; } } else{ pre[t2]=t1; root[t2]=root[a]+c-root[b]; } } printf("%d\n",ans); } return 0; }
标签:并查集
原文地址:http://blog.csdn.net/kirito_acmer/article/details/45675607