备战数学建模九之图论-FLOYD算法

经典的图论问题

求0~4四个点中两点间的最短距离和其路径。

弗洛伊德算法的代码如下

import numpy as np
import networkx as nx
from numpy import inf
from matplotlib import pyplot as plt

def Floyd(A):
    '''
    弗洛伊德算法
    created by yzy
    2022.8.3
    '''
    # A=np.array([[inf,3,inf,2,inf],
    #    [3,inf,2,1,inf],
    #    [inf,2,inf,inf,5],
    #    [2,1,inf,inf,4],
    #    [inf,inf,5,4,inf]])
    n,m=A.shape
    dis=A #邻接矩阵包含了任意两个节点之间的距离,distance
    path=np.zeros((n,n)) #初始化路由矩阵,让它都是零
    for k in range(n):
        for i in range(n):
            for j in range(n):
                if dis[i][k]+dis[k][j]<dis[i][j]:
                    dis[i][j]=dis[i][k]+dis[j][k] #找到经过k点时路径更短,接受这个更短的路径长度
                    path[i][j]=k #路由矩阵记录路径
    print("dis:",dis) #显示每对顶点最短路径长度
    print("path:",path) #显示路由矩阵
    #我们以0到4 点为例,最短距离是6。path[0][4]=3,该路径经过点3,反向追踪:path[0][3]=0,结束;正向追踪:
    # path[3][4]=0,结束。最短路径就是0->3->4。看一看前面的图,的确符合事实。

def drawMat(A):
    '''
    画无向赋权图
    created by yzy
    2022.8.3
    '''
    # A=np.mat([[0,3,0,2,0],
    #    [3,0,2,1,0],
    #    [0,2,0,0,5],
    #    [2,1,0,0,4],
    #    [0,0,5,4,0]]) #邻接矩阵
    G=nx.Graph(A) #无向赋权图
    pos=nx.shell_layout(G) #布局设置
    w=nx.get_edge_attributes(G,"weight") #获取权重
    nx.draw_networkx(G=G,pos=pos,node_size=260) #画网络图
    nx.draw_networkx_edge_labels(G=G,pos=pos,font_size=12,edge_labels=w) #标注权重
    plt.show()

if __name__ == '__main__':

 A=np.array([[inf,3,inf,2,inf],
    [3,inf,2,1,inf],
    [inf,2,inf,inf,5],
    [2,1,inf,inf,4],
    [inf,inf,5,4,inf]])
 n, m = A.shape

 #这里注意,B=A赋值法是错的,地址没变,只能一个元素一个元素的赋值
 B=np.zeros((n,n))
 for i in range(n):
     for j in range(n):
         B[i][j]=A[i][j]
 for i in range(n):
     # print(i),是从0到n-1哦
     for j in range(n):
         if A[i][j]==inf :
             B[i][j]=0
# print("A",A)
# print("B",B)
drawMat(B)
Floyd(A)

 

 输出的一个是路由矩阵,一个是距离矩阵

代码里一个是画图的,一个是算矩阵的

要手动修改邻接矩阵,自己看着图手写出来邻接矩阵

输出结果为

 

dis: [[4. 3. 5. 2. 6.]
 [3. 2. 2. 1. 5.]
 [5. 2. 4. 3. 5.]
 [2. 1. 3. 2. 4.]
 [6. 5. 5. 4. 8.]]
path: [[3. 0. 1. 0. 3.]
 [0. 3. 0. 0. 3.]
 [1. 0. 1. 1. 0.]
 [0. 0. 1. 1. 0.]
 [3. 3. 0. 0. 3.]]

path的含义代码里有解释

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值