最小生成樹圖文詳解(Prim演算法)
阿新 • • 發佈:2018-11-17
最小生成樹
就像幾個村莊都不相通, 要修路, 怎麼修, 這個花的錢最少, 這種最優選擇就是最小生成樹
設G = (V, E)是無向連通圖(V是結點集, E是邊集),相對於村莊例子,V就是那些村莊的集合,E就是村莊之間路的集合 設T = (U, TE)是最小生成樹, U是結點集,TE是邊集 Prim演算法的思想
設陣列adjvex[n]表示候選最短邊的領接點 設陣列lowcast[n]表示權值 其值如下,含義是候選最短邊(i,j)的權值為w,其中i∈V-U , j∈U adjvex[i] = j lowcost[i] = w
介紹了這麼多抽象概念,還是看圖理解一下Prim演算法的流程
設G = (V, E)是無向連通圖(V是結點集, E是邊集),相對於村莊例子,V就是那些村莊的集合,E就是村莊之間路的集合 設T = (U, TE)是最小生成樹, U是結點集,TE是邊集 Prim演算法的思想
- 首先在V集合中任意選擇一個村莊作為起始點i,將i點併入U集合中,然後在找一個修路到i村莊最便宜的j村莊併入集合TE中(在所有i∈U, j∈V-U中找一條代價最小的邊(i,j))
- 重複第一步的操作
設陣列adjvex[n]表示候選最短邊的領接點 設陣列lowcast[n]表示權值 其值如下,含義是候選最短邊(i,j)的權值為w,其中i∈V-U , j∈U adjvex[i] = j lowcost[i] = w
介紹了這麼多抽象概念,還是看圖理解一下Prim演算法的流程
C語言實現
#include<stdio.h> #define MaxSize 100 struct MGraph { int vertex[MaxSize];// 定義存放頂點的一維陣列 int edge[MaxSize][MaxSize]; // 存放邊的二維陣列 int vertexNum, edgeNum; }; int MinEdge(int *lowcost, int num) { int min = 9999; int index = -1; for(int i = 0; i < num; i++) { if(lowcost[i] < min && lowcost[i] != 0) { min = lowcost[i]; index = i; } } return index; } void Prim(MGraph *G, int v) {// 從頂點V出發 int i, j, k; int adjvex[MaxSize], lowcost[MaxSize]; for (i = 0; i < G -> vertexNum; i++) {// 初始化 lowcost[i] = G -> edge[v][i]; adjvex[i] = v; } lowcost[v] = 0; /* 將頂點v加入集合*/ for (k = 1; k < G -> vertexNum; k++) { j = MinEdge(lowcost, G -> vertexNum);// 尋找最短邊的領接點 printf("(%d, %d)%d ", j, adjvex[j], lowcost[j]);// 輸出最短邊(j, i)及其權值 lowcost[j] = 0; /* 將頂點j加入集合*/ for (i = 0; i < G ->vertexNum; i++) { /* 更新 */ if (G -> edge[i][j] < lowcost[i]) { lowcost[i] = G -> edge[i][j]; adjvex[i] = j; } } } } int main() { MGraph g; MGraph *G = &g; G -> vertexNum = 6;//6個頂點 G -> edgeNum = 9;// 9條邊 for(int i = 0; i < 6; i++) for(int j = 0; j < 6; j++) G -> edge[i][j] = 9999;// 無限大 G -> edge[0][1] = 34; G -> edge[1][0] = 34; G -> edge[0][2] = 46; G -> edge[2][0] = 46; G -> edge[0][5] = 19; G -> edge[5][0] = 19; G -> edge[1][4] = 12; G -> edge[4][1] = 12; G -> edge[2][3] = 17; G -> edge[3][2] = 17; G -> edge[2][5] = 25; G -> edge[5][2] = 25; G -> edge[3][4] = 38; G -> edge[4][3] = 38; G -> edge[3][5] = 25; G -> edge[5][3] = 25; G -> edge[4][5] = 26; G -> edge[5][4] = 26; Prim(G, 0); }
參考書籍:資料結構(王紅德 皮德常)