并集-查找算法

用于判断图中节点对的连通性

快速查找:
#include<stdio.h>
#define N 10000
main()
{
    int i,p,q,t,id[N];
    for(i=0;i<N;i++) id[i]=i;
    while(scanf("%d%d\n",&p,&q)==2)
    {
        if(id[p]==id[q]) continue;
        for(t=id[p],i=0;i<N;i++)
            if(id[i]==t) id[i]=id[q];
        printf("%d %d\n",p,q);
    }
}
优点:查找操作只需查看数组中的值是否相等
缺点:每次做并集操作需遍历整个数组
快速并集:
#include<stdio.h>
#define N 10000
main()
{
    int i,j,p,q,id[N];
    for(i=0;i<N;i++) id[i]=i;
    while(scanf("%d%d\n",&p,&q)==2)
    {
        for(i = p; i != id[i]; i = id[i]);//遍历至根
        for(j = q; j != id[j]; j = id[j]);//遍历至根
        if(i==j) continue;//根一样在一个集合里
        id[i] = j;//并集
        printf("%d %d\n",p,q);
    }
}
优点:并集操作很快,查找需依赖输入特性生成的树的扁平情况
缺点:树可能退化成单链表,例如:输入样例1-2,2-3,3-4,4-5...
加权快速并集:
#include<stdio.h>
#define N 10000
main()
{
    int i,j,p,q,id[N],sz[N];//sz[N]用来记录每个集合中的节点个数
    for(i=0;i<N;i++)
    {
        id[i]=i;
        sz[i]=1;
    }
    while(scanf("%d%d\n",&p,&q)==2)
    {
        for(i = p; i != id[i]; i = id[i]);//遍历至根
        for(j = q; j != id[j]; j = id[j]);//遍历至根
        if(i==j) continue;
        if(sz[i] < sz[j])//做并集处理时,并入节点数较小的根
        {
            id[i] = j;
            sz[j] += sz[i];
        }
        else
        {
            id[j] = i;
            sz[i] += sz[j];
        }
        printf("%d %d\n",p,q);
    }
}
算法性能理想
对分路径压缩加权快速并集:
#include<stdio.h>
#define N 10000
main()
{
    int i,j,p,q,id[N],sz[N];//sz[N]用来记录每个集合中的节点个数
    for(i=0;i<N;i++)
    {
        id[i]=i;
        sz[i]=1;
    }
    while(scanf("%d%d\n",&p,&q)==2)
    {
        //对分压缩路径
        for(i = p; i != id[i]; i = id[i])
            id[i] = id[id[i]];
        for(j = q; j != id[j]; j = id[j])
            id[j] = id[id[j]];
        if(i==j) continue;
        if(sz[i] < sz[j])//做并集处理时,并入节点数较小的根
        {
            id[i] = j;
            sz[j] += sz[i];
        }
        else
        {
            id[j] = i;
            sz[i] += sz[j];
        }
        printf("%d %d\n",p,q);
    }
}
算法性能理想
posted @ 2012-08-18 15:03  ArthurSJiang  阅读(488)  评论(0编辑  收藏  举报