#include <iostream>
#include <map>
using namespace std;
//不相交集合森林
typedef struct disjoint_set_forest_node{
int value;//结点值
disjoint_set_forest_node *parent;//父亲结点
disjoint_set_forest_node *next;//next结点,形成单向循环链表
int rank;//结点的秩
}disjoint_set_forest_node,*pDisjoint_set_forest_node;
pDisjoint_set_forest_node make_set(int value)
{
pDisjoint_set_forest_node pdfn=new disjoint_set_forest_node;
pdfn->rank=0;
pdfn->parent=pdfn;
pdfn->value=value;
pdfn->next=pdfn;//单向循环链表
return pdfn;
}
pDisjoint_set_forest_node find_set(map<int,pDisjoint_set_forest_node>ma,int key)//递归版本
{
if(ma[key]!=ma[key]->parent){
ma[key]->parent=find_set(ma,ma[key]->parent->value);
}
return ma[key]->parent;
}
pDisjoint_set_forest_node find_set_iterator(map<int,pDisjoint_set_forest_node>ma,int key)//非递归版本
{
pDisjoint_set_forest_node pdfn=ma[key];
while(pdfn!=pdfn->parent){
pdfn=pdfn->parent;
}//找根结点
pDisjoint_set_forest_node pt=ma[key];
pDisjoint_set_forest_node ptmp=pt;
while(ptmp!=pdfn){
ptmp=ptmp->parent;
pt->parent=pdfn;
pt=ptmp;
}
return pdfn;
}
void link(pDisjoint_set_forest_node px,pDisjoint_set_forest_node py)//合并2个结点
{
if(px->rank<py->rank){
px->parent=py;
}else{
py->parent=px;
if(px->rank==py->rank){
++px->rank;
}
}
pDisjoint_set_forest_node ptmp=py->next;//连接两个单向循环链表,形成一个大的单向循环链表
py->next=px->next;
px->next=ptmp;
}
void union_dis(int x,int y,map<int,pDisjoint_set_forest_node>ma)//合并两颗树
{
link(find_set(ma,x),find_set(ma,y));
}
void print_set(map<int,pDisjoint_set_forest_node>ma,int x)// 打印结点信息
{
pDisjoint_set_forest_node pt=ma[x];
pDisjoint_set_forest_node ptmp=pt;
do{
cout<<ptmp->value<<" ";
ptmp=ptmp->next;
}while(pt!=ptmp);
cout<<endl;
}
int main()
{
int n=16;
pDisjoint_set_forest_node *pdf=new pDisjoint_set_forest_node[n];
map<int,pDisjoint_set_forest_node>ma;//保存值和其对应的地址之间的关系
for(int i=0;i<n;++i){
pdf[i]=make_set(i);
ma[i]=pdf[i];
}
for(int i=0;i<n;i+=2){
union_dis(i,i+1,ma);
}
for(int i=0;i<n-3;i+=4){
union_dis(i,i+2,ma);
}
union_dis(0,4,ma);
union_dis(10,12,ma);
union_dis(0,9,ma);
cout<<find_set(ma,10)->value<<endl;
cout<<find_set(ma,15)->value<<endl;
for(int i=0;i<n;++i){
print_set(ma,i);
}
for(int i=0;i<n;++i){
delete ma[i];
}
delete [] pdf;
}
#include <iostream>
#include <map>
using namespace std;
struct queue;//声明
typedef struct disjoint_set_node{
queue *represent;//指向该结点的代表
int value;
disjoint_set_node *next;//下一个结点指针
}disjoint_set_node,*pDisjoint_set_node;
typedef struct queue{
disjoint_set_node *head;
disjoint_set_node *tail;
int size;
}queue,*pQueue;
pQueue make_set(int value)//创建结点集合
{
pQueue qu=new queue;
pDisjoint_set_node pd=new disjoint_set_node;
pd->value=value;
pd->next=NULL;
pd->represent=qu;
qu->head=pd;
qu->tail=pd;
qu->size=1;
return qu;
}
int find_set(pQueue *pq,map<int,int> ma,int c)//查找结点所属的集合
{
return pq[ma[c]]->head->value;
}
void union_dis(pQueue &px,pQueue &py,map<int,int>& ma)//合并两个集合
{
if(px && py && px!=py){
int x_num=px->size,y_num=py->size;
if(x_num<y_num){
pQueue tmp=py;
py=px;
px=tmp;
}
px->size+=py->size;
px->tail->next=py->head;//链接链表
px->tail=py->tail;
pDisjoint_set_node pd=py->head;
for(int i=0;i<py->size;++i){
ma[pd->value]=ma[px->head->value];
pd->represent=px;
pd=pd->next;
}
delete py;//将多余的头结点删除掉
py=NULL;
if(x_num<y_num){
py=px;
px=NULL;
}
}
}
void main()
{
int n=16;
pQueue *pq=new pQueue[n];
map<int,int>ma;//存储结点所属集合索引
int *c=new int[n];
for(int i=0;i<n;++i){
c[i]=i;
pq[i]=make_set(c[i]);
ma[c[i]]=i;
cout<<"[ "<<c[i]<<" , "<<i<<" ] ";
}
cout<<endl;
for(int i=0;i<n;i+=2){
union_dis(pq[ma[c[i]]],pq[ma[c[i+1]]],ma);
}
for(int i=0;i<n-3;i+=4){
union_dis(pq[ma[c[i]]],pq[ma[c[i+2]]],ma);
}
union_dis(pq[ma[c[0]]],pq[ma[c[4]]],ma);
union_dis(pq[ma[c[10]]],pq[ma[c[12]]],ma);
union_dis(pq[ma[c[0]]],pq[ma[c[9]]],ma);
cout<<find_set(pq,ma,1)<<endl;
cout<<find_set(pq,ma,8)<<endl;
for(int i=0;i<n;++i){//删除结点信息
if(pq[i]){
pDisjoint_set_node pd=pq[i]->head;
pDisjoint_set_node pt=pd;
for(int j=0;j<pq[i]->size;++j){
pt=pd;
pd=pd->next;
cout<<pt->value<<" ";
delete pt;
}
delete pq[i];
cout<<endl;
}
}
cout<<endl;
delete[]c;
map<int,int>().swap(ma);
ma.clear();
}