假设我有一个矩阵MxN,填充0到5之间的值。我现在想确定该矩阵中最大的连接树,其中矩阵的值被认为是节点。如果节点在水平或垂直方向上彼此相邻,并且如果两个节点的值相同,则称一对节点是连接的。树的大小等于树中的节点。
一个例子:
1 0 3 0 0 2 2 0 0 0 0 0
1 1 2 2 2 0 2 0 0 0 0 0
0 1 0 3 0 0 2 0 0 0 0 2
3 1 0 3 0 0 2 0 2 2 2 2
0 0 0 0 0 0 0
3 0 0 3 3 0 0
3 3 3 3 0 0 0
在左侧,左侧的1个节点构成最大的树。在右侧,3个节点形成最大的树,而另外两个树由2个节点组成。
我知道我可以做一个简单的深度优先搜索,但我想知道是否有一些众所周知的我缺少的东西,可能是在图理论领域(比如Kruskal的最小生成树算法,但是对于这个例子)。
答案 0 :(得分:0)
有效地,您正在寻找的是Connected组件。 连接组件是一组节点,您可以从任何节点前往该组件中的任何其他节点。
连接组件通常适用于图表。可以使用BFS/DFS
找到连接的组件,并且从给定邻接矩阵输入的算法复杂性角度来看,没有更好的方法可以做到这一点。算法的运行时间为O(N^2)
,其中N
是图表中的多个节点。
在您的情况下,图表具有更多约束,例如每个节点最多可以与其他4个节点相邻。使用BFS/DFS
,这会为您提供O(4N) = O(N)
的运行时间,其中N是节点数。不可能有一个复杂度更高的算法,因为在最坏的情况下你需要至少考虑一次每个节点。
答案 1 :(得分:0)
您正在寻找不相交的集合,因此我建议使用不相交的数据结构和查找/并集算法:
请参阅http://en.wikipedia.org/wiki/Disjoint-set_data_structure#Disjoint-set_forests
并集操作是对称的,因此当比较的元素具有相同的值时,您实际上只需要将矩阵的每个元素与其右边的邻居及其邻居进行比较,然后应用union操作。
使用find操作再次扫描每个元素,以计算每个元素的大小,跟踪最大值。您将需要存储计数。
计算复杂度为O(MN A -1 (MN,MN))其中A -1 是逆Ackermann函数,其中一个可以考虑小对于MN的任何有用值,常数(<5)。额外的存储复杂性将是O(MN)。