python实现最短路径的实例方法


Posted in Python onJuly 19, 2020

最短路径问题(python实现)

解决最短路径问题:(如下三种算法)

(1)迪杰斯特拉算法(Dijkstra算法)
(2)弗洛伊德算法(Floyd算法)
(3)SPFA算法

第一种算法:

Dijkstra算法

广度优先搜索解决赋权有向图或者无向图的单源最短路径问题.是一种贪心的策略

算法的思路

声明一个数组dis来保存源点到各个顶点的最短距离和一个保存已经找到了最短路径的顶点的集合:T,初始时,原点s的路径权重被赋为0(dis[s]=0)。若对于顶点s存在能直接到达的边(s,m),则把dis[m]设为w(s, m),同时把所有其他(s不能直接到达的)顶点的路径长度设为无穷大。初始时,集合T只有顶点s。

然后,从dis数组选择最小值,则该值就是源点s到该值对应的顶点的最短路径,并且把该点加入到T中,OK,此时完成一个顶点,再看看新加入的顶点是否可以到达其他顶点并且看看通过该顶点到达其他点的路径长度是否比源点直接到达短,如果是,那么就替换这些顶点在dis中的值,然后,又从dis中找出最小值,重复上述动作,直到T中包含了图的所有顶点。

第二种算法:

Floyd算法

原理:

Floyd算法(弗洛伊德算法)是一种在有向图中求最短路径的算法。它是一种求解有向图中点与点之间最短路径的算法。
用在拥有负权值的有向图中求解最短路径(不过不能包含负权回路)

流程:

有向图中的每一个节点X,对于图中过的2点A和B,

如果有Dis(AX)+ Dis(XB)< Dis(AB),那么使得Dis(AB)=Dis(AX)+Dis(XB)。

当所有的节点X遍历完后,AB的最短路径就求出来了。

示例一:

#-*- coding:utf-8 -*-
 #python实现Floyd算法
 
N = 4 
_=float('inf')   #无穷大 
 graph = [[ 0, 2, 6, 4],[ _, 0, 3, _],[ 7, _, 0, 1],[ 5, _,12, 0]] 
 path = [[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1]]    #记录路径,最后一次经过的点
def back_path(path,i,j):      #递归回溯
while(-1 != path[i][j]):
   back_path(path,i,path[i][j])
    back_path(path,path[i][j],j)
   print path[i][j],14    
 return;
  return;
print "Graph:\n",graph
for k in range(N):
 for i in range(N):
   for j in range(N):
      if graph[i][j] > graph[i][k] + graph[k][j]:
       graph[i][j] = graph[i][k] + graph[k][j]
      path[i][j] = k
 print "Shortest distance:\n",graph
 print "Path:\n",path
 print "Points pass-by:"
 for i in range(N):
 for j in range(N):
   print "%d -> %d:" % (i,j),
    back_path(path,i,j)
    print "\n",

示例二:

#!usr/bin/env python#encoding:utf-8
'''
功能:使用floyd算法求最短路径距离
'''
import random
import time
def random_matrix_genetor(vex_num=10):  
  '''
  随机图顶点矩阵生成器
  输入:顶点个数,即矩阵维数  
  '''
  data_matrix=[]  
  for i in range(vex_num):
    one_list=[]    
    for j in range(vex_num):
      one_list.append(random.randint(1, 100))
    data_matrix.append(one_list)  
    return data_matrixdef floyd(data_matrix):  
    '''
  输入:原数据矩阵,即:一个二维数组
  输出:顶点间距离  '''
  dist_matrix=[]
  path_matrix=[]
  vex_num=len(data_matrix) 
  for h in range(vex_num):
    one_list=['N']*vex_num
    path_matrix.append(one_list)
    dist_matrix.append(one_list)  
  for i in range(vex_num):    
    for j in range(vex_num):
      dist_matrix=data_matrix
      path_matrix[i][j]=j  
  for k in range(vex_num):    
    for i in range(vex_num):      
      for j in range(vex_num):        
        if dist_matrix[i][k]=='N' or dist_matrix[k][j]=='N':
          temp='N'
        else:
          temp=dist_matrix[i][k]+dist_matrix[k][j]        
        if dist_matrix[i][j]>temp:
          dist_matrix[i][j]=temp
          path_matrix[i][j]=path_matrix[i][k]  
  return dist_matrix, path_matrixdef main_test_func(vex_num=10):  
   '''
   主测试函数
   '''
  data_matrix=random_matrix_genetor(vex_num)
  dist_matrix, path_matrix=floyd(data_matrix)  
  for i in range(vex_num):    
  for j in range(vex_num):      
  print '顶点'+str(i)+'----->'+'顶点'+str(j)+'最小距离为:', dist_matrix[i][j]
if __name__ == '__main__':
  data_matrix=[['N',1,'N',4],[1,'N',2,'N'],['N',2,'N',3],[4,'N',3,'N']]
  dist_matrix, path_matrix=floyd(data_matrix)  
  print dist_matrix  
  print path_matrix
 
  time_list=[] 
  print '------------------------------节点数为10测试情况------------------------------------'
  start_time0=time.time()
  main_test_func(10)
  end_time0=time.time()
  t1=end_time0-start_time0
  time_list.append(t1)  
  print '节点数为10时耗时为:', t1 
  print '------------------------------节点数为100测试情况------------------------------------'
  start_time1=time.time()
  main_test_func(100)
  end_time1=time.time()
  t2=end_time1-start_time1
  time_list.append(t2)  
  print '节点数为100时耗时为:', t2 
  print '------------------------------节点数为1000测试情况------------------------------------'
  start_time1=time.time()
  main_test_func(1000)
  end_time1=time.time()
  t3=end_time1-start_time1
  time_list.append(t3)  
  print '节点数为100时耗时为:', t3 
  print '--------------------------------------时间消耗情况为:--------------------------------'
  for one_time in time_list:    
  print one_time

示例三:

import numpy as np
Max   = 100
v_len  = 4
edge  = np.mat([[0,1,Max,4],[Max,0,9,2],[3,5,0,8],[Max,Max,6,0]])
A    = edge[:]
path  = np.zeros((v_len,v_len)) 
 
def Folyd():  
  for i in range(v_len):    
    for j in range(v_len):      
      if(edge[i,j] != Max and edge[i,j] != 0):
        path[i][j] = i 
  print 'init:'
  print A,'\n',path  
  for a in range(v_len):    
    for b in range(v_len):      
      for c in range(v_len):        
        if(A[b,a]+A[a,c]<A[b,c]):
          A[b,c] = A[b,a]+A[a,c]
          path[b][c] = path[a][c]  
  print 'result:'      
  print A,'\n',path        
 
if __name__ == "__main__":
  Folyd()

第三种算法:

SPFA算法是求解单源最短路径问题的一种算法,由理查德·贝尔曼(Richard Bellman) 和 莱斯特·福特 创立的。有时候这种算法也被称为 Moore-Bellman-Ford 算法,因为 Edward F. Moore 也为这个算法的发展做出了贡献。它的原理是对图进行V-1次松弛操作,得到所有可能的最短路径。

其优于迪科斯彻算法的方面是边的权值可以为负数、实现简单,缺点是时间复杂度过高,高达 O(VE)。但算法可以进行若干种优化,提高了效率。

思路:

我们用数组dis记录每个结点的最短路径估计值,用邻接表或邻接矩阵来存储图G。我们采取的方法是动态逼近法:设立一个先进先出的队列用来保存待优化的结点,优化时每次取出队首结点u,并且用u点当前的最短路径估计值对离开u点所指向的结点v进行松弛操作,如果v点的最短路径估计值有所调整,且v点不在当前的队列中,就将v点放入队尾。这样不断从队列中取出结点来进行松弛操作,直至队列空为止。

Python 相关文章推荐
python将人民币转换大写的脚本代码
Feb 10 Python
python实现2014火车票查询代码分享
Jan 10 Python
让Python更加充分的使用Sqlite3
Dec 11 Python
python实现爬取图书封面
Jul 05 Python
Python进阶之自定义对象实现切片功能
Jan 07 Python
Python设计模式之外观模式实例详解
Jan 17 Python
python操作gitlab API过程解析
Dec 27 Python
OpenCV中VideoCapture类的使用详解
Feb 14 Python
python3 实现口罩抽签的功能
Mar 11 Python
Jupyter Notebook折叠输出的内容实例
Apr 22 Python
详解pandas赋值失败问题解决
Nov 29 Python
解决Pytorch修改预训练模型时遇到key不匹配的情况
Jun 05 Python
python等待10秒执行下一命令的方法
Jul 19 #Python
python怎么删除缓存文件
Jul 19 #Python
python实现从ftp上下载文件的实例方法
Jul 19 #Python
python中关于数据类型的学习笔记
Jul 19 #Python
Python趣味实例,实现一个简单的抽奖刮刮卡
Jul 18 #Python
用python给csv里的数据排序的具体代码
Jul 17 #Python
python如何删除列为空的行
Jul 17 #Python
You might like
Yii框架关联查询with用法分析
2014/12/02 PHP
php字符串过滤与替换小结
2015/01/26 PHP
PHP环境搭建(php+Apache+mysql)
2016/11/14 PHP
window.open的功能全解析
2006/10/10 Javascript
JSON.stringify 语法实例讲解
2012/03/14 Javascript
json的定义、标准格式及json字符串检验
2014/05/11 Javascript
JavaScript判断数组重复内容的两种方法(推荐)
2016/06/06 Javascript
Jquery ajax请求导出Excel表格的实现代码
2016/06/08 Javascript
Ajax跨域实现代码(后台jsp)
2017/01/21 Javascript
EasyUI Datebox 日期验证之开始日期小于结束时间
2017/05/19 Javascript
使用jQuery实现简单的tab框实例
2017/08/22 jQuery
基于Bootstrap实现城市三级联动
2017/11/23 Javascript
vue如何在自定义组件中使用v-model
2018/05/14 Javascript
详解Vue、element-ui、axios实现省市区三级联动
2019/05/07 Javascript
JavaScript提升机制Hoisting详解
2019/10/23 Javascript
微信小程序中网络请求缓存的解决方法
2019/12/29 Javascript
使用element-ui +Vue 解决 table 里包含表单验证的问题
2020/07/17 Javascript
Windows上配置Emacs来开发Python及用Python扩展Emacs
2015/11/20 Python
python Django批量导入不重复数据
2016/03/25 Python
python实现字符串中字符分类及个数统计
2018/09/28 Python
解析Python3中的Import
2019/10/13 Python
Python: tkinter窗口屏幕居中,设置窗口最大,最小尺寸实例
2020/03/04 Python
html5组织内容_动力节点Java学院整理
2017/07/10 HTML / CSS
Staples美国官方网站:办公用品一站式采购
2016/07/28 全球购物
法国一家芭蕾舞鞋公司:Repetto
2018/11/12 全球购物
Christys’ Hats官网:英国帽子制造商
2018/11/28 全球购物
啤酒销售实习自我鉴定
2013/09/24 职场文书
教育英语专业毕业生的求职信
2014/03/13 职场文书
绩效工资实施方案
2014/03/15 职场文书
财产公证书
2014/04/10 职场文书
工作作风懒散检讨书
2014/10/29 职场文书
教师个人工作总结范文2015
2015/10/14 职场文书
Python实现简单的猜单词
2021/06/15 Python
Java GUI编程菜单组件实例详解
2022/04/07 Java/Android
利用Python实现模拟登录知乎
2022/05/25 Python
GoFrame基于性能测试得知grpool使用场景
2022/06/21 Golang