在线等价类与离线等价类(概念)


1.定义:等价类是指相互等价的元素的最大集合。

2.在线等价类

  ⑴ 初始时,只有n个元素,每个元素属于一个独立的等价类。

  ⑵需要执行以下操作:

              把包含a,b的等价类合并成一个类combina(a,b);  确定哪个类包含元素e,即确定两个元素是否在同一Find(e);不同类返回不同结果。combina(a,b) 等效i=Find(a), j=Find(b); if(i!=j) Union(i,j);

  ⑶解决方案: 将每个集合(类)描述为一棵树,采用链表的方法来描述树。每个节点必须有一个parent域,但不必有children域 。节点内的数字是其parent域的值,节点外的数字为其索引。索引同时也就是该节点所表示的元素。根节点的 parent域被置为0;


在线等价类与离线等价类(概念)_第1张图片

  ⑷代码实现:

         int Find(int e)

           {

                 while(!root[e])

                      e= parent[e];

                 returne;

         }

高度规则:若树i的高度小于树j的高度,则将j作为i的父节点。

重量规则:若树i的节点数大于树j的节点数,则将j作为i的父节点。

在合并算法中,每个节点上增加 一个布尔域root,若当前节点为跟节点,则其root域为true,

每个根节点的parent域用来保存该树中节点的总数。

             voidUnion(int i, int j)    //将根为i,j的两棵树进行合并;

             {  

                 if(parent[i]< parent[j])

                 {

                                   parent[j]+= parent[i];

                                   root[i]= false;

                                   parent[i]= j;

                            }    

                            else

                            {

                                   parent[i]+= parent[j];

                                   root[j]= false;

                                   parent[j]= i;

                            }

              }

路径压缩:

在线等价类与离线等价类(概念)_第2张图片

 int Find(int e)

{

      Int j = e;

      while(!root[j])   //搜索根节点

           j =parent[j];

       int f =e;

      while(f!=j)

      {

              Int pf= parent[f];

              Parent[f]= j;

              F =pf;

      }

      return j;

}

3.离线等价类

  离线等价类的输入时元素数目n,关系数目r以及r对关系,问题的目标是吧n个元素分配至相应的等价类中。

 


你可能感兴趣的:(数据结构)