当前位置: 首页 > wzjs >正文

做专题页的背景网站app制作公司

做专题页的背景网站,app制作公司,网站建设业务员主要工作,网站规划教学设计目录 prim算法 kruskal算法 题目练习 (1)AcWing 858. Prim算法求最小生成树 - AcWing (2)859. Kruskal算法求最小生成树 - AcWing题库​编辑 学习之前建议温习一下迪杰斯特拉算法和并查集~ 先简单认识下最小生成树&#xff1a…

目录

 prim算法

 kruskal算法

题目练习 

(1)AcWing 858. Prim算法求最小生成树 - AcWing

 (2)859. Kruskal算法求最小生成树 - AcWing题库​编辑


学习之前建议温习一下迪杰斯特拉算法和并查集~ 

       先简单认识下最小生成树:

         最小生成树是所有节点的最小连通子图,即:以最小的成本(边的权值)将图中所有节点链接到一起。图中有n个节点,那么一定可以用n-1条边将所有节点连接到一起。那么如何选择这n-1条边就是最小生成树算法的任务所在。

        下面我们以一道模板题来讲解如何解决这个问题~~

 prim算法

        prim算法是从节点的角度采用贪心的策略每次寻找距离最小生成树最近的节点并加入到最小生成树中。prim算法核心就是三步,一定要熟悉这三步,代码相对会好些很多:

  1. 第一步,选距离生成树最近节点
  2. 第二步,最近节点加入生成树
  3. 第三步,更新非生成树节点到生成树的距离(即更新minDist数组,minDist数组用来记录每一个节点距离最小生成树的最近距离

 下面按照这三步解决一下刚刚的题目~

        ① 初始化mindist数组为 10001【默认每个节点距离最小生成树是最大的,这样后面我们在比较的时候,发现更近的距离,才能更新到minDist数组上】

        ② 选距离生成树最近节点:刚开始还没有最小生成树,所以随便选一个节点加入就好(因为每一个节点一定会在最小生成树里,所以随便选一个就好),那我们选择节点1(符合遍历数组的习惯,第一个遍历的也是节点1)----->最近节点加入生成树:  此时节点1已经算最小生成树的节点-------->更新非生成树节点到生成树的距离(即更新minDist数组,如下图)

        ③选距离生成树最近节点 :选取一个距离最小生成树(节点1)最近的非生成树里的节点,节点2,3,5距离最小生成树(节点1)最近,选节点2(其实选节点3或者节点2都可以,距离一样的)加入最小生成树---->最近节点加入生成树:此时节点1和节点2,已经算最小生成树的节点---->更新非生成树节点到生成树的距离(即更新minDist数组)\

        ④最小生成树(节点1、节点2),节点3,6距离最小生成树(节点1、节点2)最近,选节点3(选节点6也可以,距离一样)加入最小生成树----->此时节点1、节点2、节点3算是最小生成树的节点。----->更新与生成树结点相连接的非生成树节点到生成树的距离 

  • 节点4和节点3的距离为1,和原先的距离值2小,所以更新minDist[4]为1。

 .....

......

......

最后节点7加入最小生成树

        绿色的边将所有节点链接到一起,并且保证权值是最小的,因为我们在更新minDist数组的时候,都是选距离最小生成树最近 的点加入到树中 

我们要求最小生成树里边的权值总和就是把最后的minDist数组累加一起

 完整代码

#include<bits/stdc++.h>
using namespace std;
int main()
{int v,e;cin>>v>>e;//邻接矩阵存储图 1-based索引vector<vector<int>> grid(v+1,vector<int>(v+1,10001));while(e--){int x,y,k;cin>>x>>y>>k;//双向图grid[x][y]=k;grid[y][x]=k;}//所有结点到最小生成树的最小距离vector<int> mindist(v+1,10001);// 这个结点是否在树里vector<bool> isintree(v+1,false);//循环n-1次,建立n-1条边=就可以把n个结点的图连接在一起for(int i=1;i<v;i++){//1、选距离生成树最近的节点int cur=-1;int minval=INT_MAX;for(int j=1;j<=v;j++) //1 - v,顶点编号,这里下标从1开始{if(!isintree[j]&&mindist[j]<minval){minval=mindist[j];cur=j;}}//2、最近节点加入生成树isintree[cur]=true;//3、更新非生成树节点到生成树的距离(即更新minDist数组)//只需要关心与 cur 相连的非生成树节点的距离是否比原非生成树节点到生成树节点的距离更小了呢for(int j=1;j<=v;j++){if(!isintree[j]&&grid[cur][j]<mindist[j])mindist[j]=grid[cur][j];}}//统计结果int result=0;for(int i=2;i<=v;i++)//不计第一个顶点,因为统计的是边的权值,v个节点有 v-1条边{result+=mindist[i];}cout<<result;}

 真的和dijstrk求最短路径的模板很像!!!


 kruskal算法

用另外一种算法求解上题,prim 算法是维护节点的集合,而 Kruskal 是维护边的集合

kruscal的思路:

  • 边的权值排序,因为要优先选最小的边加入到生成树里
  • 遍历排序后的边
    • 如果边首尾的两个节点在同一个集合,说明如果连上这条边图中会出现环
    • 如果边首尾的两个节点不在同一个集合,加入到最小生成树,并把两个节点加入同一个集合

下面我们画图举例说明kruskal的工作过程。

开始从头遍历排序后的边

判断两个节点是否在同一个集合,就看图中两个节点是否有绿色的粗线连着就行 

.......

.......

 

 在代码中,如果将两个节点加入同一个集合,又如何判断两个节点是否在同一个集合呢

 这里就涉及到我们之前讲解的并查集:数据结构--并查集-高效处理连通性问题-CSDN博客

完整代码 

#include<bits/stdc++.h>
using namespace std;
const int N=10001;
vector<int> fa(N,-1);//并查集标记节点关系的数组
int find(int x){if(x==fa[x]) return x;else return fa[x]=find(fa[x]);
}
void merge(int x,int y)
{int xx=find(x);int yy=find(y);if(xx==yy) return ;fa[yy]=xx;
}
struct Edge
{int l,r,val;// l,r为 边两边的节点,val为边的数值//定义结构体的排序规则bool operator<(const Edge& other) const{return val < other.val;}
};
int main()
{int v,e;cin>>v>>e;vector<Edge> edges;//存储图while(e--){int v1, v2, val;cin>>v1>>v2>>val;edges.push_back({v1,v2,val});}//并查集初始化for(int i=0;i<N;i++) fa[i]=i;//执行kruskal算法int result_val=0;//1、排序sort(edges.begin(),edges.end());//从头开始遍历边for(auto edge:edges){//找出两个节点的祖先int x=find(edge.l);int y=find(edge.r);//如果祖先不同则不在一个集合if(x!=y) {result_val+=edge.val;//这条边可以计入生成树的边merge(x,y);//两个结点加入一个集合}}cout<<result_val;return 0;}

我觉得这个更简单诶 


图是稀疏图,点很多但边很少---->kruskal算法

图是稠密图,几乎每个点都和其他点有边相连,点多边多---->prim算法


题目练习 

(1)AcWing 858. Prim算法求最小生成树 - AcWing

m很大,几乎每个点都和其他点有边相连,适用Prim算法 

#include <bits/stdc++.h>
using namespace std;int main() {int n, m;cin >> n >> m;vector<vector<int>> g(n + 1, vector<int>(n + 1, 10001)); // 初始化为较大的值while (m--) {int u, v, w;cin >> u >> v >> w;if (w < g[u][v]) { // 处理重边,保留最小边权g[u][v] = w;g[v][u] = w; //无向边}}vector<int> dist(n + 1, 10001); // 存储各节点到MST的最小距离vector<bool> visited(n + 1, false);dist[1] = 0; // 起始节点初始化为0int total = 0;for (int i = 0; i < n; ++i) { // 需要选择n次,最后一次确认连通性int u = -1, minDist = 10001;for (int j = 1; j <= n; ++j) {if (!visited[j] && dist[j] < minDist) {minDist = dist[j];u = j;}}if (u == -1) { // 无法找到有效节点,图不连通cout << "impossible";return 0;}visited[u] = true;total += dist[u]; // 累加边权// 更新相邻节点的距离for (int v = 1; v <= n; ++v) {if (!visited[v] && g[u][v] < dist[v]) {dist[v] = g[u][v];}}}cout << total;return 0;
}

 (2)859. Kruskal算法求最小生成树 - AcWing题库

n这麽多,m也这麽多,图很大,适合使用 Kruskal 算法

#include<bits/stdc++.h>
using namespace std;
const int N=1e5+10;
vector<int> fa(N,-1);//并查集标记节点关系的数组
int find(int x){if(x==fa[x]) return x;else return fa[x]=find(fa[x]);
}
void merge(int x,int y)
{int xx=find(x);int yy=find(y);if(xx==yy) return ;fa[yy]=xx;
}
struct Edge
{int l,r,val;// l,r为 边两边的节点,val为边的数值//定义结构体的排序规则bool operator<(const Edge& other) const{return val < other.val;}
};
int main()
{int v,e;cin>>v>>e;vector<Edge> edges;//存储图while(e--){int v1, v2, val;cin>>v1>>v2>>val;edges.push_back({v1,v2,val}); //不用去重}//并查集初始化for(int i=0;i<N;i++) fa[i]=i;//执行kruskal算法int edge_count = 0; // 记录加入生成树的边数int result_val=0;//1、排序sort(edges.begin(),edges.end());//从头开始遍历边for(auto edge:edges){//找出两个节点的祖先int x=find(edge.l);int y=find(edge.r);//如果祖先不同则不在一个集合if(x!=y) {result_val+=edge.val;//这条边可以计入生成树的边merge(x,y);//两个结点加入一个集合edge_count++;if (edge_count == v - 1) break; // 提前终止:最小生成树已经完成}}if (edge_count == v - 1)cout << result_val << endl;elsecout << "impossible" << endl;return 0;}

http://www.dtcms.com/wzjs/246291.html

相关文章:

  • 网站如何做流量百度竞价点击神器
  • 网站建设 开发票实体店引流推广方法
  • 网站源码下载后怎么布置软文推广渠道
  • 深圳网站建设排名最新国际新闻头条新闻
  • wordpress软件分享泰安优化关键词排名哪家合适
  • 企业网站的一般要素包括chinaz站长素材
  • 好用的网站建设百度推广app下载
  • 电影网站做视频联盟企业推广的渠道有哪些
  • 关于解决网站 建设经费的请示全网最全搜索引擎app
  • 个人模板图片长沙网站推广seo
  • 网站开发什么百度推广费用一年多少钱
  • 官方网站建设专家磐石网络关键词排名优化软件价格
  • 有哪些做兼职的网站自动发外链工具
  • 包头球形网架公司宁波免费建站seo排名
  • 网站建设报价表表格下载优化手机流畅度的软件
  • 酒托做哪个网站好怎么自己建立网站
  • 海南做网站的技术公司seo推广优化培训
  • 建网站松滋哪家强?营销推广公司案例
  • 上海建设和交通委网站百度推广公司哪家比较靠谱
  • 做网站里面的内容谷歌推广app
  • 平台与网站有什么区别大数据营销精准营销
  • 专门做2k名单的网站品牌网
  • asp.net商务网站 包括哪些文件网站投放广告费用
  • 宛城区网站建设seo是干嘛的
  • 备案成功后怎么建设网站深圳最新消息
  • 湖南省建设厅电话谷歌优化怎么做
  • 东莞设计企业网站的有哪些互联网营销师培训费用是多少
  • 做理财的网站seort什么意思
  • 佛山美容网站建设aso优化工具
  • 扁平化网站 psd为什么sem的工资都不高