[英]Traversing through an adjacency matrix for Prim's MST algorithm
我在使用Java遍历加权邻接矩阵时遇到问题。 我想要做的是使用Prim的算法从矩阵中获得最小生成树的权重。
我到目前为止的代码如下:
public int findPrim(int[][] matrix) {
ArrayList < Integer > checkThese = new ArrayList < > ();
checkThese.add(0); //Starting vertex.
boolean[] checked = new boolean[graph.vertexCount()];
int w = 0;
int column = 0;
int row = 0;
int smallest = 0;
for (Iterator < Integer > it = checkThese.Iterator(); it.hasNext();) {
smallest = Integer.MAX_VALUE;
for (int k = 0; k < graph.vertexCount(); k++) {
if ((matrix[r][k] < smallest) && matrix[r][k] != 0 && !checked[k - 1]) {
smallest = matrix[r][k];
column = k;
}
}
if (smallest != Integer.MAX_VALUE) {
w += smallest;
checkThese.add(column);
checked[column] = true;
}
}
return w;
}
我知道如何遍历矩阵应该在纸上工作,但我遇到了实现问题。 更具体地说,因为我需要在迭代列表时更新checkThese
,我知道我需要使用迭代器,就像我尝试过的那样。 但是,现在的问题是我无法找到一种方法来获取矩阵的r
坐标,我稍后需要它。 该方法也缺少其他一些东西,但我主要担心的是如何在更新我正在检查的矩阵行列表时遍历矩阵。
我的邻接矩阵是以。的形式
A B C D E
A 0 4 2 8 0
B 0 0 5 6 7
C 0 0 0 9 3
D 0 0 0 0 1
E 0 0 0 0 0
计划是从行A
开始并选择最小边(2)。 之后,我将C
列排除在考虑范围之外,然后检查A
行和C
行,依此类推,直到我排除所有列,从而检查所有边。
您需要另一个嵌套循环来使其按照您指示的方式工作。 这是修正后的伪代码。
let n be the number of vertices
initialize cost <- 0
initialize checkThese <- [0]
initialize checked <- [true, false, ..., false] (length n)
repeat n - 1 times (alternatively, test for termination as indicated)
smallest <- infinity
argSmallest <- null
for v in checkThese
for w from 0 to n - 1
let cost = matrix[min(v, w)][max(v, w)]
if not checked[w] and cost < smallest then
smallest <- cost
argSmallest <- w
end if
end for
end for
(break here if argSmallest is null)
cost <- cost + smallest
add argSmallest to checkThese
checked[argSmallest] <- true
end repeat
这不是Prim算法特别有效的实现。 为了加速从O(n ^ 3)到O(n ^ 2),密集矩阵的渐近最优,你可以维护另一个n元素的整数数组,称之为minCost
。 索引w
处的条目是从检查顶点到w
的边的最小成本。 修改后的伪代码看起来像这样。
let n be the number of vertices
initialize cost <- 0
initialize checked <- [true, false, ..., false] (length n)
initialize minCost <- [0, infinity, ..., infinity] (length n)
repeat n - 1 times (alternatively, test for termination as indicated)
smallest <- infinity
argSmallest <- null
for w from 0 to n - 1
if not checked[w] and minCost[w] < smallest then
smallest <- minCost[w]
argSmallest <- w
end if
end for
(break here if argSmallest is null)
cost <- cost + smallest
checked[argSmallest] <- true
minCost[argSmallest] <- 0
for v from 0 to n - 1
let cost = matrix[min(argSmallest, v)][max(argSmallest, v)]
if not checked[v] and cost < minCost[v] then
minCost[v] <- cost
end if
end for
end repeat
如果所有边缘成本都是正数,那么您可以用minCost[w] > 0
替换测试checked[w]
并minCost[w] > 0
checked
数组。 你也可以融合两个循环。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.