码迷,mamicode.com
首页 > 其他好文 > 详细

最小生成树

时间:2019-07-31 11:18:22      阅读:111      评论:0      收藏:0      [点我收藏+]

标签:tps   out   algorithm   int   联通   sign   push   col   mic   

 INTRODUCTION

一个有 n 个结点的连通图的生成树是原图的极小连通子图,且包含原图中的所有 n 个结点,并且有保持图连通的最少的边。 最小生成树可以用kruskal(克鲁斯卡尔)算法或prim(普里姆)算法求出。

--百度百科

概述

在一给定的无向图G = (V, E) 中,(u, v) 代表连接顶点 u 与顶点 v 的边(即),而 w(u, v) 代表此的权重,若存在 T 为 E 的子集(即)且为无循环图,使得

的 w(T) 最小,则此 T 为 G 的最小生成树

技术图片

最小生成树其实是最小权重生成树的简称。

--百度百科

最小生成树的性质:

最小生成树性质:设G=(V,E)是一个连通网络,U是顶点集V的一个非空真子集。若(u,v)是G中一条“一个端点在U中(例如:u∈U),另一个端点不在U中的边(例如:v∈V-U),且(u,v)具有最小权值,则一定存在G的一棵最小生成树包括此边(u,v)。--百度百科

通俗来说

对于一个连通图,若已经求出最小生成树A,则若能找出最小生成树B与A不同

则这个图中,至少有两条边边权相等,且两条边在同一个环上,删去这两条边中的任意一条不影响原图的连通性,

且在生成树A,B中等边权的边的数量相等

 推论

 

对于一个连通图,将他制成一颗生成树,使他的最大边最小,则这棵树是该图的最小生成树

不存在比最小生成树中最大边i更小的边j,当j将i替换后原图联通,若替换后仍联通,则j的权值必定比i大

因为在求最小生成树时已经保证最小联通

最小生成树的求法:

1,Kruskal

大致思路在于将每一条边按照边权从小到大排序,之后按这个顺序扫一遍,若这条边的起点和终点尚未联通或间接联通,那加上这条边,把这两个点连起来,那么怎么判断联通呢?自然要靠并查集了

 1 #include<iostream>
 2 #include<cstdio>
 3 #include<algorithm>
 4 #include<vector>
 5 using namespace std;
 6 int f[100086];
 7 struct edge
 8 {
 9     int from;
10     int to;
11     int weight;
12 };
13 int n, m;
14 int tot;
15 long long ans;
16 vector<edge>e;
17 int find(int x)//普通的并查集
18 {
19     if (f[x] == x)
20         return x;
21     else
22         return f[x] = find(f[x]);
23 }
24 void merge(int a, int b)
25 {
26     int x = find(a);
27     int y = find(b);
28     if (f[x] != f[y])
29         f[y] = x;
30 }
31 bool cmp(edge a, edge b)
32 {
33     return a.weight < b.weight;
34 }
35 int main()
36 {
37     cin >> n >> m;
38     for (int i = 1; i <= n; i++)
39         f[i] = i;//并查集初始化
40     for (int i = 1; i <= m; i++)
41     {
42         int x, y, z;
43         cin >> x >> y >> z;
44         edge t;
45         t.from = x;
46         t.to = y;
47         t.weight = z;
48         e.push_back(t);
49         t.from = y;
50         t.to = x;
51         e.push_back(t);
52     }
53     sort(e.begin(), e.end(), cmp);
54     for (int i = 0; i < e.size(); i++)
55     {
56         if (find(e[i].from) != find(e[i].to))
57         {
58             merge(e[i].from, e[i].to);
59             ans += e[i].weight;
60         }
61     }
62     cout << ans << endl;
63     return 0;
64 }

2,Prim

最小生成树

标签:tps   out   algorithm   int   联通   sign   push   col   mic   

原文地址:https://www.cnblogs.com/HNFOX/p/11274539.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!