并查集 平凡的测试数据

传送门:http://cogs.pro/cogs/problem/problem.php?pid=2089

            第一眼看就是“银河英雄传说”,其实只是类似,异或和有神奇的地方。

       首先,find时,只有fx!=find(fx)时,才更改sum[x],因为维护的是前缀和(感性理解),sum[x]不仅是自己的,而且异或了fx的,所以sum[x]不能多次更改,最后也要去掉f[x](就是多异或个fx)。

#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<iostream>
#include<algorithm>
using namespace std;
int n,m,a[300005],f[300005],sum[300005];
int read()
{
	int sum=0,f=1;char x=getchar();
	while(x<'0'||x>'9'){if(x=='-')f=-1;x=getchar();}
	while(x>='0'&&x<='9')sum=sum*10+x-'0',x=getchar();
	return sum*f;
}
int find(int x)
{
	if(f[x]==x)
	   return x;
	int k=find(f[x]);
	if(k!=f[x])
	{
	   sum[x]^=sum[f[x]];
	   f[x]=k;
	}
	return f[x];
}
int main()
{
	freopen("td.in","r",stdin);
	freopen("td.out","w",stdout);
	n=read();m=read();
	for(int i=1;i<=n;i++)
	{
	   sum[i]=a[i]=read(),f[i]=i;
	}
	int x,y,z;
	while(m--)
	{
		z=read();
		if(z==1)
		{
			x=read(),y=read();
			f[x]=y;
		}
		else
		{
			x=read();
			find(x);
			if(f[x]==x)printf("%d
",sum[x]);
			else
			   printf("%d
",sum[x]^sum[f[x]]);
		}
	}
}

原文地址:https://www.cnblogs.com/QTY2001/p/7632778.html