最小生成樹之kruskal演算法(結構體實現)

2021-09-23 06:21:27 字數 2021 閱讀 1565

【演算法思想】:演算法對權值從小到大排序,每次選取當前權值最小的邊加入結點,直到所有的結點都已加入結點。演算法中用到了並查集的思想(並查集),通過並查集來判斷兩個結點是否有共同的父節點,如果有,則表明兩個結點已經聯通。如果沒有,就將兩個結點聯通,記錄路徑。

使用結構體陣列來存圖;

struct node

mp[n]; //定義乙個結構體陣列來存圖;

分為三部分:

(1)初始化:使每個結點的初始根節點為自己,並且每個結點構成一顆樹,樹的深度是1;

(2)查詢:使用遞迴來查詢每個結點的父親結點;

(3)合併:將不同父節點的結點合併;

注:這裡的並查集是優化後的,即:進行了路徑壓縮。如果題目中無要求,可以只寫簡單的並查集演算法。

void inin(int n)

}int find(int x) //找每個結點的父親結點;

}bool join(int a,int b) //將兩個不同父節點的結點合併

else

par[fa] = fb;

} return true;

}

變數每個結點;

int kruskal(int m)

} return sum;

}

kuskal演算法完整**實現:

#include

#include

#include

using namespace std;

#define n 1000

int par[n]

;//記錄父親結點

int rank1[n]

;//樹的深度;

int sum;

//最短路徑

struct node

mp[n]

;//定義乙個結構體陣列來存圖;

bool cmp

(node a,node b)

//對邊的權值進行從小到大排序

void

inin

(int n)

}int

find

(int x)

//找每個結點的父親結點;

}bool join

(int a,

int b)

//將兩個不同父節點的結點合併

else

par[fa]

= fb;

}return true;

}int

kruskal

(int m)

}return sum;

}int

main()

sum =0;

kruskal

(m);

cout << sum << endl;

return0;

}

輸入樣例1:5個點,8條邊,

5 8

1 2 3

1 3 7

2 3 10

2 4 4

2 5 8

3 4 6

3 5 2

4 5 17

輸出:

輸入樣例2:9個點,14條邊,

9 14

1 2 4

2 3 8

3 4 7

4 5 9

5 6 10

6 7 2

7 8 1

8 9 7

2 8 11

3 9 2

7 9 6

3 6 4

4 6 14

1 8 8

輸出:37

最小生成樹之Kruskal演算法

最小生成樹 kruskal演算法描述 該演算法是基於貪心的思想得到的。首先我們把所有的邊按照權值先從小到大排列,接著按照順序選取每條邊,如果這條邊的兩個端點不屬於同一集合,那麼就將它們合併,直到所有的點都屬於同乙個集合為止。合併頂點可以利用並查集,換而言之,kruskal演算法就是基於並查集的貪心演...

最小生成樹之kruskal演算法

先構造乙個只含 n 個頂點 而邊集為空的子圖,把子圖中各個頂點看成各棵樹上的根結點,之後,從網的邊集 e 中選取一條權值最小的邊,若該條邊的兩個頂點分屬不同的樹,則將其加入子圖,即把兩棵樹合成一棵樹,反之,若該條邊的兩個頂點已落在同一棵樹上,則不可取,而應該取下一條權值最小的邊再試之。依次類推,直到...

最小生成樹之kruskal演算法

克魯斯卡爾 kruskal 演算法過程 構造最小生成樹 u,te 1.置u的初值等於v 即包含有g中的全部頂點 te的初值為空集 即圖t中每乙個頂點都構成乙個連通分量 2.將圖g中的邊按權值從小到大的順序依次選取 若選取的邊未使生成樹t形成迴路,則加入te 否則捨棄,直到te中包含 n 1 條邊為止...