码迷,mamicode.com
首页 > 其他好文 > 详细

加权并查集

时间:2017-09-22 22:38:14      阅读:215      评论:0      收藏:0      [点我收藏+]

标签:oid   回车   遍历   自己   表示   log   etc   换行   bool   

  加权并查集是一种特殊的并查集,除可提供查询操作外,还可用于表示元素与其代表元素的关系。下面以食物链为例,讲解一下加权并查集。

#include<cstdio> //调用cstdio库,使用getchar函数
#include<cctype> //调用cctype库,使用isdigit函数,返回参数是否为整数
int N,K,ans,r,x,y; //定义变量用于有几个动物,几句话,答案,以及动物的关系和两个要描述的动物 
int f[50005],d[50005]; //定义数组记录代表元素,以及到达代表元素的距离 
inline int get_num() { //内联get_num函数,读入整数
    int num = 0; //定义整型变量num,并赋值为0
    char c; //定义字符型变量c
    bool flag = false; //定义布尔值变量flag,并置为假
    while ((c = getchar()) == ‘ ‘ || c == ‘\n‘ || c == ‘\r‘); //忽略开头的空格,换行符及回车符
    if (c == ‘-‘) flag = true; //如果读到负号,就将负数标志置为真
    else num = c - ‘0‘;    //否则将读到的第一个数字保存;
    while (isdigit(c = getchar())) //只要读入的还是数字,就循环
        num = num * 10 + c - ‘0‘; //将num整体前移一位,并将新读入的一位数字保存
    return (flag ? -1 : 1) * num; //返回读到的整数,若负数标志为真,就返回其相反数,即一个负数
}
int find(int i) { //定义函数查询代表元素以及到达代表元素的距离 
	if(i==f[i]) return i; //找到代表元素返回 
	int oldf=f[i]; //记录下元素之前的代表元素
	f[i]=find(f[i]); //更新元素的代表元素 
	d[i]=(d[i]+d[oldf])%3; //更新元素与代表元素的距离 
	return f[i]; //返回代表元素 
}
void check(int r,int x,int y) { //定义函数检查是否为假话 
	if(x>N||y>N) {++ans;return;} //若动物编号超出范围,则为假话 
	if(r==2&&x==y) {++ans;return;} //若说动物自己吃自己,则为假话 
	if(find(x)==find(y)) { //若两个动物在同一集合中 
		if((d[x]-d[y]+3)%3!=r-1) ++ans;return; //动物之间的距离不符合描述,则为假话 
	}
	else {
		d[f[x]]=(3-d[x])%3; //求出代表元素到该元素的距离 
		f[f[x]]=x;f[x]=y; //让代表元素指向该元素,即该元素成为代表元素,并指向y 
		d[f[y]]=(3-d[y])%3; //同上 
		f[f[y]]=y;f[y]=y;d[y]=0; // 同上,并让y成为代表元素,令其到代表元素的距离为0 
		if(r==1) d[x]=0; //若为同类,则x到y距离为0 
		else d[x]=1; //若x吃y,则x到y距离为1 
		/* 另一种合并方法 
		f[f[y]]=f[x]; //让y的代表元素指向x的代表元素 
		d[f[y]]=(d[x]-d[y]-(r-1)+3)%3; //更新y的代表元素到其代表元素的距离 
		*/ 
	}
}
int main() {
	N=read();K=read(); //读入N,K 
	for(int t=1;t<=N;++t) f[t]=t; //初始化每个元素的代表元素 
	for(int t=1;t<=K;++t) { //遍历每句话 
		r=read();x=read();y=read(); //读入r,x,y
		check(r,x,y); //调用check函数 
	}
	printf("%d",ans); //打印答案 
	return 0;
}

 

加权并查集

标签:oid   回车   遍历   自己   表示   log   etc   换行   bool   

原文地址:http://www.cnblogs.com/Mr94Kevin/p/7577102.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!