python最小生成树kruskal与prim算法详解


Posted in Python onJanuary 17, 2019

kruskal算法基本思路:先对边按权重从小到大排序,先选取权重最小的一条边,如果该边的两个节点均为不同的分量,则加入到最小生成树,否则计算下一条边,直到遍历完所有的边。

prim算法基本思路:所有节点分成两个group,一个为已经选取的selected_node(为list类型),一个为candidate_node,首先任取一个节点加入到selected_node,然后遍历头节点在selected_node,尾节点在candidate_node的边,选取符合这个条件的边里面权重最小的边,加入到最小生成树,选出的边的尾节点加入到selected_node,并从candidate_node删除。直到candidate_node中没有备选节点(这个循环条件要求所有节点都有边连接,即边数要大于等于节点数-1,循环开始前要加入这个条件判断,否则可能会有节点一直在candidate中,导致死循环)。

#coding=utf-8
class Graph(object):
  def __init__(self, maps):
    self.maps = maps
    self.nodenum = self.get_nodenum()
    self.edgenum = self.get_edgenum()
 
  def get_nodenum(self):
    return len(self.maps)
 
  def get_edgenum(self):
    count = 0
    for i in range(self.nodenum):
      for j in range(i):
        if self.maps[i][j] > 0 and self.maps[i][j] < 9999:
          count += 1
    return count
 
  def kruskal(self):
    res = []
    if self.nodenum <= 0 or self.edgenum < self.nodenum-1:
      return res
    edge_list = []
    for i in range(self.nodenum):
      for j in range(i,self.nodenum):
        if self.maps[i][j] < 9999:
          edge_list.append([i, j, self.maps[i][j]])#按[begin, end, weight]形式加入
    edge_list.sort(key=lambda a:a[2])#已经排好序的边集合
    
    group = [[i] for i in range(self.nodenum)]
    for edge in edge_list:
      for i in range(len(group)):
        if edge[0] in group[i]:
          m = i
        if edge[1] in group[i]:
          n = i
      if m != n:
        res.append(edge)
        group[m] = group[m] + group[n]
        group[n] = []
    return res
 
  def prim(self):
    res = []
    if self.nodenum <= 0 or self.edgenum < self.nodenum-1:
      return res
    res = []
    seleted_node = [0]
    candidate_node = [i for i in range(1, self.nodenum)]
    
    while len(candidate_node) > 0:
      begin, end, minweight = 0, 0, 9999
      for i in seleted_node:
        for j in candidate_node:
          if self.maps[i][j] < minweight:
            minweight = self.maps[i][j]
            begin = i
            end = j
      res.append([begin, end, minweight])
      seleted_node.append(end)
      candidate_node.remove(end)
    return res
 
max_value = 9999
row0 = [0,7,max_value,max_value,max_value,5]
row1 = [7,0,9,max_value,3,max_value]
row2 = [max_value,9,0,6,max_value,max_value]
row3 = [max_value,max_value,6,0,8,10]
row4 = [max_value,3,max_value,8,0,4]
row5 = [5,max_value,max_value,10,4,0]
maps = [row0, row1, row2,row3, row4, row5]
graph = Graph(maps)
print('邻接矩阵为\n%s'%graph.maps)
print('节点数据为%d,边数为%d\n'%(graph.nodenum, graph.edgenum))
print('------最小生成树kruskal算法------')
print(graph.kruskal())
print('------最小生成树prim算法')
print(graph.prim())

初始的图如下。

python最小生成树kruskal与prim算法详解

运行结果如下。

python最小生成树kruskal与prim算法详解

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
python实现排序算法
Feb 14 Python
Python的Flask框架中使用Flask-Migrate扩展迁移数据库的教程
Jun 14 Python
python发送邮件功能实现代码
Jul 15 Python
Python3的urllib.parse常用函数小结(urlencode,quote,quote_plus,unquote,unquote_plus等)
Sep 18 Python
深入浅出分析Python装饰器用法
Jul 28 Python
pandas.DataFrame选取/排除特定行的方法
Jul 03 Python
pytorch之Resize()函数具体使用详解
Feb 27 Python
Spark处理数据排序问题如何避免OOM
May 21 Python
详解pandas获取Dataframe元素值的几种方法
Jun 14 Python
正确的理解和使用Django信号(Signals)
Apr 14 Python
python tkinter实现定时关机
Apr 21 Python
pytorch MSELoss计算平均的实现方法
May 12 Python
解决PyCharm不运行脚本,而是运行单元测试的问题
Jan 17 #Python
在PyCharm导航区中打开多个Project的关闭方法
Jan 17 #Python
Python设计模式之模板方法模式实例详解
Jan 17 #Python
Python设计模式之外观模式实例详解
Jan 17 #Python
Python pycharm 同时加载多个项目的方法
Jan 17 #Python
Python设计模式之建造者模式实例详解
Jan 17 #Python
在Pycharm中修改文件默认打开方式的方法
Jan 17 #Python
You might like
增加反向链接的101个方法 站长推荐
2007/01/31 PHP
Phpbean路由转发的php代码
2008/01/10 PHP
关于PHP二进制流 逐bit的低位在前算法(详解)
2013/06/13 PHP
深入解读php中关于抽象(abstract)类和抽象方法的问题分析
2014/01/03 PHP
javascript第一课
2007/02/27 Javascript
Jquery 点击按钮显示和隐藏层的代码
2011/07/25 Javascript
js 实现日期灵活格式化的小例子
2013/07/14 Javascript
JavaScript之数组(Array)详解
2015/04/01 Javascript
JavaScript事件 &quot;事件对象&quot;的注意要点
2016/01/14 Javascript
JavaScript tab选项卡插件实例代码
2016/02/23 Javascript
Bootstrap嵌入jqGrid,使你的table牛逼起来
2016/05/05 Javascript
JS中parseInt()和map()用法分析
2016/12/16 Javascript
AngularJS学习第二篇 AngularJS依赖注入
2017/02/13 Javascript
vue页面使用阿里oss上传功能的实例(一)
2017/08/09 Javascript
js仿微信抢红包功能
2020/09/25 Javascript
Vue递归组件+Vuex开发树形组件Tree--递归组件的简单实现
2019/04/01 Javascript
微信小程序导航栏跟随滑动效果的实现代码
2019/05/14 Javascript
JavaScript中的ES6 Proxy的具体使用
2019/06/16 Javascript
详解Element-UI中上传的文件前端处理
2019/08/07 Javascript
Layui Form 自定义验证的实例代码
2019/09/14 Javascript
vue实现树形结构样式和功能的实例代码
2019/10/15 Javascript
echarts.js 动态生成多个图表 使用vue封装组件操作
2020/07/19 Javascript
python实现TCP服务器端与客户端的方法详解
2015/04/30 Python
python 对多个csv文件分别进行处理的方法
2019/01/07 Python
python函数修饰符@的使用方法解析
2019/09/02 Python
input元素的url类型和email类型简介
2012/07/11 HTML / CSS
销售所有的狗狗产品:Dog.com
2016/10/13 全球购物
财务部出纳岗位职责
2013/12/22 职场文书
致跳远运动员广播稿
2014/02/11 职场文书
中班开学寄语
2014/04/04 职场文书
旅游安全协议书
2014/04/21 职场文书
优秀教研组申报材料
2014/12/26 职场文书
未来,这5大方向都很适合创业
2019/07/22 职场文书
7个你应该知道的JS原生错误类型
2021/04/29 Javascript
JavaScript声明变量和数据类型的转换
2022/04/12 Javascript
Ubuntu Server 安装Tomcat并配置systemctl
2022/04/28 Servers