所以我必须拿一个ID数组
0 1 2 3 4 5 6 7 8 9
0 1 2 3 4 5 6 7 8 9
并对其执行加权快速联合。我必须执行9-0,3-4,5-8,7-2,2-1,5-7,0-3和4-2的操作。这是我对这些操作所做的数组:
9-0
0 1 2 3 4 5 6 7 8 9
9 1 2 3 4 5 6 7 8 9
3-4
0 1 2 3 4 5 6 7 8 9
9 1 2 3 3 5 6 7 8 9
5-8
0 1 2 3 4 5 6 7 8 9
9 1 2 3 3 5 6 7 5 9
7-2
0 1 2 3 4 5 6 7 8 9
9 1 7 3 3 5 6 7 5 9
2-1
0 1 2 3 4 5 6 7 8 9
9 7 7 3 3 5 6 7 5 9
5-7
0 1 2 3 4 5 6 7 8 9
9 7 7 3 3 7 6 7 5 9
0-3
0 1 2 3 4 5 6 7 8 9
9 7 7 3 3 7 6 7 5 3
4-2
0 1 2 3 4 5 6 7 8 9
9 7 7 3 3 7 6 3 5 9
问题是ID数组操作会有所不同,具体取决于您是使用快速查找还是快速联合或加权快速联合。这对于加权快速结合是否正确?这是我用于加权快速联合的代码:
public class WeightedQuickUnionUF
{
private int[] id; // parent link (site indexed)
private int[] sz; // size of component for roots (site indexed)
private int count; // number of components
public WeightedQuickUnionUF(int N)
{
count = N;
id = new int[N];
for (int i = 0; i < N; i++) id[i] = i;
sz = new int[N];
for (int i = 0; i < N; i++) sz[i] = 1;
}
public int count()
{ return count; }
public boolean connected(int p, int q)
{ return find(p) == find(q); }
private int find(int p)
{ // Follow links to find a root.
while (p != id[p]) p = id[p];
return p;
}
public void union(int p, int q)
{
int i = find(p);
int j = find(q);
if (i == j) return;
// Make smaller root point to larger one.
if (sz[i] < sz[j]) { id[i] = j; sz[j] += sz[i]; }
else { id[j] = i; sz[i] += sz[j]; }
count--;
}
}
加权快速联合的代码向您展示它是如何工作的,但基本上它是一种Union-find,它将两棵树连接在一起。使用加权快速联合,您始终将较小的树连接到较大的树。 ID数组是树的表示,其中顶行和底行有数字。如果顶部的数字与底部匹配,那么该数字是林中的根,但是例如如果顶部数字是9而底部数字是0则表示9是0的子节点.ID数组从9开始单节点树和像9-0这样的操作将两棵树连接在一起。