如题,在看完题解后,很多人(包括我自己)可能会尝试跳过 Floyd 传递联通关系的步骤,直接用“单向并查集”做法像普通并查集一样维护信息,即:
- 在并查集的树形结构中,若 i 是 j 的父亲,则表示 i 愿意将资料拷贝给 j(下文简写为“i→j”)。
- 对于新增的 i→j 的情况,将 i 所在连通块的根与 j 本身合并。
(之所以“单向并查集”打引号是因为这好像不是并查集的一种正确应用)
但实际上这种做法有漏洞,因为它在维护传递关系的过程中会丢失部分信息。以如下样例为例:
3
2 0
1 0
2 0
1
如果用“单向并查集”直接维护的话:
- 将 2 的父亲设为 1 所在连通块的根,即 1 本身;
- 将 1 的父亲设为 2 所在连通块的根。因为进行了第一步的操作,所以此时的根还是 1 本身,相当于没有操作;
- 将 2 的父亲设为 3 所在连通块的根,即 3;
可以画图理解一下,此时所有操作结束,森林中剩下两棵树,分别以 1 和 3 为根。答案为 2。
但实际上只需 1 张光盘足矣,因为 2→1,3→2,传递得 3→1。
造成这种现象的原因在于第二步操作因为已经有了 1→2 的关系,将 2→1 的关系丢失了,导致将 2 指向 3 的时候无法将 1 同时指向 3。
因此,在本题中,单纯使用上述解法是错误的。