克鲁斯卡尔算法打印最小生成树:

  构造出所有边的集合 edges,从小到大,依次选出筛选边打印,遇到闭环(形成回路)时跳过。

JS代码:

 //定义邻接矩阵
let Arr2 = [
[0, 10, 65535, 65535, 65535, 11, 65535, 65535, 65535],
[10, 0, 18, 65535, 65535, 65535, 16, 65535, 12],
[65535, 18, 0, 22, 65535, 65535, 65535, 65535, 8],
[65535, 65535, 22, 0, 20, 65535, 65535, 16, 21],
[65535, 65535, 65535, 20, 0, 26, 65535, 7, 65535],
[11, 65535, 65535, 65535, 26, 0, 17, 65535, 65535],
[65535, 16, 65535, 65535, 65535, 17, 0, 19, 65535],
[65535, 65535, 65535, 16, 7, 65535, 19, 0, 65535],
[65535, 12, 8, 21, 65535, 65535, 65535, 65535, 0],
] let numVertexes = 9, //定义顶点数
numEdges = 15; //定义边数 // 定义图结构
function MGraph() {
this.vexs = []; //顶点表
this.arc = []; // 邻接矩阵,可看作边表
this.numVertexes = null; //图中当前的顶点数
this.numEdges = null; //图中当前的边数
}
let G = new MGraph(); //创建图使用 //创建图
function createMGraph() {
G.numVertexes = numVertexes; //设置顶点数
G.numEdges = numEdges; //设置边数 //录入顶点信息
for (let i = 0; i < G.numVertexes; i++) {
G.vexs[i] = 'V' + i; //scanf('%s'); //ascii码转字符 //String.fromCharCode(i + 65);
}
console.log(G.vexs) //打印顶点 //邻接矩阵初始化
for (let i = 0; i < G.numVertexes; i++) {
G.arc[i] = [];
for (j = 0; j < G.numVertexes; j++) {
G.arc[i][j] = Arr2[i][j]; //INFINITY;
}
}
console.log(G.arc); //打印邻接矩阵
} function Edge() {
this.begin = 0;
this.end = 0;
this.weight = 0;
} function Kruskal() {
let n, m;
let parent = []; //定义一数组用来判断边与边是否形成环路
let edges = []; //定义边集数组 for (let i = 0; i < G.numVertexes; i++) {
for (let j = i; j < G.numVertexes; j++) { //因为是无向图所以相同的边录入一次即可,若是有向图改为0
if (G.arc[i][j] != 0 && G.arc[i][j] != 65535) {
let edge = new Edge();
edge.begin = i;
edge.end = j;
edge.weight = G.arc[i][j];
edges.push(edge);
}
}
} edges.sort((v1, v2) => {
return v1.weight - v2.weight
}); console.log('**********打印所有边*********');
console.log(edges); for (let i = 0; i < G.numVertexes; i++) {
parent[i] = 0;
} for (let i = 0; i < edges.length; i++) {
n = Find(parent, edges[i].begin)
m = Find(parent, edges[i].end)
if (n != m) { //假如n与m不等,说明此边没有与现有生成树形成环路
parent[n] = m;
console.log("(%s,%s) %d", G.vexs[edges[i].begin], G.vexs[edges[i].end], edges[i].weight);
}
}
} function Find(parent, f) { //查找连线顶点的尾部下标
while (parent[f] > 0) {
f = parent[f]
}
return f;
} createMGraph();
console.log('*********打印最小生成树**********')
Kruskal();

打印结果:

代码部分过程解析:

 
当i=7时,第82行,调用Find函数,会传入参数edges[7].begin=5。此时第94行,parent[5]=8>0,所以f=8,再循环得parent[8]=6。因parent[6]=0 所以Find返回后第82行得到n=6。而此时第83行,传入参数edges[7].end=6得到m=6。此时n=m,不再打印,继续下一循环。这就告诉我们,因为(V5,V6)使得边集合A形成了环路。因此不能将它纳入到最小生成树中。
当i=8时,与上面相同,由于边(V1,V2)使得边集合A形成了环路,因此不将它纳入最小生成树。

克鲁斯卡尔算法主要针对边展开,时间复杂度为 O(elog e),e为图的边数,普利姆算法的时间复杂度为O(n²),n为最小生成树的边数。所以,边数少(稀疏图)用克鲁斯卡尔算法,边数多(稠密图)用普利姆算法。

参考文献: 程杰《大话数据结构》

JS实现最小生成树之克鲁斯卡尔(Kruskal)算法的更多相关文章

  1. 图的生成树(森林)(克鲁斯卡尔Kruskal算法和普里姆Prim算法)、以及并查集的使用

    图的连通性问题:无向图的连通分量和生成树,所有顶点均由边连接在一起,但不存在回路的图. 设图 G=(V, E) 是个连通图,当从图任一顶点出发遍历图G 时,将边集 E(G) 分成两个集合 T(G) 和 ...

  2. 洛谷P3366【模板】最小生成树-克鲁斯卡尔Kruskal算法详解附赠习题

    链接 题目描述 如题,给出一个无向图,求出最小生成树,如果该图不连通,则输出orz 输入输出格式 输入格式: 第一行包含两个整数N.M,表示该图共有N个结点和M条无向边.(N<=5000,M&l ...

  3. 最小生成树之克鲁斯卡尔(kruskal)算法

    #include <iostream> #include <string> using namespace std; typedef struct MGraph{ string ...

  4. 图解最小生成树 - 克鲁斯卡尔(Kruskal)算法

    我们在前面讲过的<克里姆算法>是以某个顶点为起点,逐步找各顶点上最小权值的边来构建最小生成树的.同样的思路,我们也可以直接就以边为目标去构建,因为权值为边上,直接找最小权值的边来构建生成树 ...

  5. 克鲁斯卡尔(Kruskal)算法求最小生成树

    /* *Kruskal算法求MST */ #include <iostream> #include <cstdio> #include <cstring> #inc ...

  6. 克鲁斯卡尔(Kruskal)算法

    # include <stdio.h> # define MAX_VERTEXES //最大顶点数 # define MAXEDGE //边集数组最大值 # define INFINITY ...

  7. MST最小生成树及克鲁斯卡尔(Kruskal)算法

    最小生成树MST,英文名如何拼写已忘,应该是min spaning tree吧.假设一个无向连通图有n个节点,那么它的生成树就是包括这n个节点的无环连通图,无环即形成树.最小生成树是对边上权重的考虑, ...

  8. 最小生成树——Kruskal(克鲁斯卡尔)算法

    [0]README 0.1) 本文总结于 数据结构与算法分析, 源代码均为原创, 旨在 理解 Kruskal(克鲁斯卡尔)算法 的idea 并用 源代码加以实现: 0.2)最小生成树的基础知识,参见 ...

  9. 最小生成树---Prim算法和Kruskal算法

    Prim算法 1.概览 普里姆算法(Prim算法),图论中的一种算法,可在加权连通图里搜索最小生成树.意即由此算法搜索到的边子集所构成的树中,不但包括了连通图里的所有顶点(英语:Vertex (gra ...

随机推荐

  1. 小程序:位置信息(Location)及微信小程序LBS解决方案实践

    目前在做的小程序需要使用到map组件以及小程序个性地图,涉及到的功能如下: 1# 获取用户当前位置,返回对应的省市区 2# 根据目的地的具体地址,显示在地图中的位置 3# 根据用户当前位置,计算出 与 ...

  2. BZOJ4283: 魔法少女伊莉雅(最短路径图+最短路径树)

    题面 传送门 题解 太长了不想写了→_→ 题解 //minamoto #include<bits/stdc++.h> #define R register #define inf 0x3f ...

  3. [javascript]—jQuery解析本地 XML 文档

    Create a jQuery object using an XML string and obtain the value of the title node. <!doctype html ...

  4. http协议缓存小结

    缓存可以使用expire方式,设置到期时间,缓存的时间等于expire设置的时间减去当前的时间 也可以使用no-cache的方式进行缓存,当设置了no-cache的方式时,以no-cache的为准,e ...

  5. P5242 [USACO19FEB]Cow Dating

    题目链接 题意分析 首先我们可以得出计算公式 \[s_i=\prod_{k=1}^i(1-p_k)\] \[f_i=\sum_{k=1}^i\frac{p_k}{1-p_k}\] 那么 \[ans(i ...

  6. knova绘制进度条

    效果: 源码: <!DOCTYPE html> <html lang="en"> <head> <meta charset="U ...

  7. linux如何安装和启动mongdb

    1.下载安装包 下载地址: https://www.mongodb.com/dr/fastdl.mongodb.org/linux/mongodb-linux-x86_64-4.0.9.tgz/dow ...

  8. dubbo和zookeeper的关系

    转载前言:网络上很多教程没有描述zookeeper和dubbo到底是什么关系.分别扮演了什么角色等信息,都是说一些似是而非的话,这里终于找到一篇文章,比较生动地描述了注册中心和微服务框架之间的关系,以 ...

  9. Java简易撞鬼游戏demo

    9*9方格内两点随机行走,相遇则停止. public class 撞鬼 { public static int length = 9; public static char[][] matrix = ...

  10. 如何给oneindex网盘增加评论、密码查看、read me,头提示功能。

    来自我的博客:www.resource143.com 微信公众号:资源库resource 视频教程地址 点击查看 评论功能 特性 使用 GitHub 登录 支持多语言 [en, zh-CN, zh-T ...