4872. 最短路之和(python)

看数据范围可知,时间复杂度一定小于(n**4),暴力求解肯定不行。

题目要求,求出任意两个点之间最小距离的和,那么想到Folyd算法,但是这个算法需要(n**3),并且题目询问n次,总共需要(n**4),那么想到一个一个删除点再求最小距离,相对于一个一个加点,再求最小和,跟Folyd算法流程不谋而合,例如前面有a,b点,先需要加上c点,那么这次把c当做路过的点,计算a到c再到b的距离,和原来a到b的距离进行比较。

有问题,有问题。如果这时候又加上了d点,重复上述流程,把d点当做路过的点,计算a到d再到b,a到d再到c......。看似没问题,之前是不是忘记一步?

少了从a,b经过c再到d,和d经过c再到a,b。上一步需要把所有的点经过c再到另一个点,而不是只计算a,b经过c到另一个点。

from collections import defaultdict

def floyd(ls):
    new = ls[-1]
    for i in range(n):
        for j in range(n):
            edge[i][j] = min(edge[i][j], edge[i][new] + edge[new][j] )
            
    count = 0
    
    for i in ls:
        for j in ls:
            count += edge[i][j]
    ans.append(count)

# 编号从0-n-1
# 那么x-1才为我们的编号
edge = []
v = defaultdict(int)
n = int(input())
for _ in range(n):
    edge.append(list(map(int, input().split())))
  
questions = list(map(int, input().split()))
ans = []
ls = []
for num in questions[::-1]:
    ls.append(num-1) 
    floyd(ls)

for num in ans[::-1]:
    print(num, end = ' ')

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值