AcWing 858 Prim演算法求最小生成樹

2021-09-27 07:26:47 字數 1229 閱讀 3436

題目描述:

給定乙個n個點m條邊的無向圖,圖中可能存在重邊和自環,邊權可能為負數。

求最小生成樹的樹邊權重之和,如果最小生成樹不存在則輸出impossible。

給定一張邊帶權的無向圖g=(v, e),其中v表示圖中點的集合,e表示圖中邊的集合,n=|v|,m=|e|。

由v中的全部n個頂點和e中n-1條邊構成的無向連通子圖被稱為g的一棵生成樹,其中邊的權值之和最小的生成樹被稱為無向圖g的最小生成樹。

輸入格式

第一行包含兩個整數n和m。

接下來m行,每行包含三個整數u,v,w,表示點u和點v之間存在一條權值為w的邊。

輸出格式

共一行,若存在最小生成樹,則輸出乙個整數,表示最小生成樹的樹邊權重之和,如果最小生成樹不存在則輸出impossible。

資料範圍

1≤n≤500,

1≤m≤10^5,

圖中涉及邊的邊權的絕對值均不超過10000。

輸入樣例:

4 5

1 2 1

1 3 2

1 4 3

2 3 2

3 4 4

輸出樣例:

6
分析:

prim演算法與dijkstra演算法十分類似。都是基於點集的,每次找離點集最近的點,連上點集到該點的邊。不同的是dijkstra演算法用鬆弛操作來更新最短路徑,而prim演算法只需要每次選離點集最近的點,將邊長加入最小生成樹的權重中即可。如何尋找離點集最近的點,只需修改下dijkstra演算法d陣列的含義為某點向點集中連線的邊的最小邊的長度即可。每次加入某條邊進生成樹,即用選中的邊的頂點更新其他連線邊的最短邊的長度。鑑於演算法較為簡單,具體過程見**。

#include #include #include using namespace std;

const int maxn = 505,inf = 0x3f3f3f3f;

int n,m,g[maxn][maxn],d[maxn];

bool vis[maxn];

int prim()

return res;

}int main()

int res = prim();

if(res == -1) puts("impossible");

else printf("%d\n",res);

return 0;

}

858 Prim演算法求最小生成樹

給定乙個n個點m條邊的無向圖,圖中可能存在重邊和自環,邊權可能為負數。求最小生成樹的樹邊權重之和,如果最小生成樹不存在則輸出impossible。給定一張邊帶權的無向圖g v,e 其中v表示圖中點的集合,e表示圖中邊的集合,n v m e 由v中的全部n個頂點和e中n 1條邊構成的無向連通子圖被稱為...

858 Prim演算法求最小生成樹

思路 將所有點到集合的距離初始化為正無窮 進行n次迴圈 找到不在集合中且到集合距離最近的點 用找到的點來更新其它點到集合的距離 include include include include using namespace std const int n 510 int n,m int g n n ...

Prim演算法 Kruskal演算法

一 prim演算法 1 要求 1 生成一顆連通的樹 2 生成樹 包含全部頂點,v 1條邊,沒有迴路,並且新增一條邊會變成有迴路 3 權重和最小 2 過程模擬 最重要 貪心的思想,每一步都要選擇權值最小的,這棵樹所有跟頂點相連的邊中最小的。從根節點開始,讓樹慢慢的長大。過程 從v1開始 跟v1有聯絡的...