并查集
来源:互联网 发布:电脑445端口怎么关闭 编辑:程序博客网 时间:2024/06/05 00:17
并查集
http://tyvj.cn/Problem_Show.asp?id=1111
描述:
Victoria是一位颇有成就的艺术家,他因油画作品《我爱北京天安门》闻名于世界。现在,他为了报答帮助他的同行们,准备开一个舞会。
Victoria准备邀请n个已经确定的人,可是问题来了:
这n个人每一个人都有一个小花名册,名册里面写着他所愿意交流的人的名字。比如说在A的人名单里写了B,那么表示A愿意与B交流;但是B的名单里不见的有A,也就是说B不见的想与A交流。但是如果A愿意与B交流,B愿意与C交流,那么A一定愿意与C交流。也就是说交流有传递性。
Victoria觉得需要将这n个人分为m组,要求每一组的任何一人都愿意与组内其他人交流。并求出一种方案以确定m的最小值是多少。
注意:自己的名单里面不会有自己的名字。
输入格式:
第一行输入一个n,接下来n行,每i+1行表示为编号为i的人的小花名册名单,名单以0结束。
输出格式;
一个数m。
输入样例:
18
0
18 0
0
0
11 0
0
0
0
0
0
5 0
0
0
0
0
0
0
2 0
输出样例:
16
分析:
这题要用并查集去解。
并查集模版一:
void init ( ) //集合元素个数{ for ( int i = 0; i < MAX; i++ ) parent[i] = -1; //每一个自成一个单元素集合}Find ( int x ) { if ( parent [x] < 0 ) return x; else return Find ( parent [x] ); } void Union ( int Root1, int Root2 ) { //求两个不相交集合Root1与Root2的并 parent[Root1] += parent[Root2]; parent[Root2] = Root1; //将Root2连接到Root1下面}
并查集模版二:
int parent[Max]; //记录结点的双亲 int rank[Max]; //记录结点的深度void init(int n) //初始化 { int i; for(i=0;i<=n;i++) { parent[i]=i; rank[i]=1; }} int find(int x) //查找 { int t=x, temp; while(parent[x]!=x) //找所属集合,即根结点 x=parent[x]; while(parent[t]!=x) { //路径压缩,使深度不为1的点向上浮。 temp=parent[t]; parent[t]=x; rank[t]=1; t=temp; } return x; }void merge(int x,int y) //合并 { int tx=find(x); int ty=find(y); if(tx!=ty) //路径压缩 { if (rank[tx]<rank[ty]) { parent[tx]=ty; rank[ty]+=rank[tx]; rank[tx]=1; } else { parent[ty]=tx; rank[tx]+=rank[ty]; rank[ty]=1; } } }
代码:
#include <iostream>using namespace std;#define N 204#include<cstring>int map[N][N],n,m,rant[N],parent[N];void init(int n){for(int i=1;i<=n;i++){parent[i]=i;rant[i]=0;}}int find(int x){ if(parent[x]==x) return x; else return parent[x]=find(parent[x]);}void uion(int u,int v){int fa=find(u);int fb=find(v);if(fa!=fb){if(rant[fa]<rant[fb]){parent[fa]=fb;rant[fb]+=rant[fa];rant[fa]=1;}else{parent[fb]=fa; rant[fa]+=rant[fb]; rant[fb]=1;}m--;}}int main(int argc, char *argv[]){int i ,j;cin>>n;memset(map,0,sizeof(map));for(i=1;i<=n;i++){while(cin>>j,j)map[i][j]=1;}m=n;init(n);for(i=1;i<=n;i++){for(j=1;j<=n;j++)if(map[i][j]==1&&map[j][i]==1){uion(i,j);map[i][j]=0;}}cout<<m<<endl;return 0;}
- HDU3938 并查集 并查集
- 并查集(集并查)
- HDU1232 并查集<并>
- 并查集
- 数据结构-并查集
- 并查集
- 并查集!
- 并查集
- 并查集
- 并查集
- 并查集
- 并查集总结
- 并查集学习
- 并查集
- 并查集
- 并查集
- 所谓并查集
- 并查集
- 扩展欧几里得算法
- jquery-autocomplete 参数说明
- synchronized的使用
- K次方(即求n^k的前三位与后三位)
- 记录下---datatable添加列 绑定数据---新手勿喷--笔记
- 并查集
- MessageBox的常见用法
- crontab 执行脚本***.sh 方法
- 看过的电影、电视剧里的经典台词,持续更新,欢迎把自己喜欢的经典台词留言
- 基于Linux (RHEL 5.5) 安装Oracle 10g RAC
- 集群部署weblogic+sup错误BEA-141274
- 2011-2012年度总结
- ios开发self的用法
- linux下的抓包工具tcpdump